method name="add_debugger_plugin">
			<return type="void" />
			<param index="0" name="script" type="EditorDebuggerPlugin" />
			<description>
				Adds a [Script] as debugger plugin to the Debugger. The script must extend [EditorDebuggerPlugin].
			</description>
		</method>
		<method name="add_export_platform">
			<return type="void" />
			<param index="0" name="platform" type="EditorExportPlatform" />
			<description>
				Registers a new [EditorExportPlatform]. Export platforms provides functionality of exporting to the specific platform.
			</description>
		</method>
		<method name="add_export_plugin">
			<return type="void" />
			<param index="0" name="plugin" type="EditorExportPlugin" />
			<description>
				Registers a new [EditorExportPlugin]. Export plugins are used to perform tasks when the project is being exported.
				See [method add_inspector_plugin] for an example of how to register a plugin.
			</description>
		</method>
		<method name="add_import_plugin">
			<return type="void" />
			<param index="0" name="importer" type="EditorImportPlugin" />
			<param index="1" name="first_priority" type="bool" default="false" />
			<description>
				Registers a new [EditorImportPlugin]. Import plugins are used to import custom and unsupported assets as a custom [Resource] type.
				If [param first_priority] is [code]true[/code], the new import plugin is inserted first in the list and takes precedence over pre-existing plugins.
				[b]Note:[/b] If you want to import custom 3D asset formats use [method add_scene_format_importer_plugin] instead.
				See [method add_inspector_plugin] for an example of how to register a plugin.
			</description>
		</method>
		<method name="add_inspector_plugin">
			<return type="void" />
			<param index="0" name="plugin" type="EditorInspectorPlugin" />
			<description>
				Registers a new [EditorInspectorPlugin]. Inspector plugins are used to extend [EditorInspector] and provide custom configuration tools for your object's properties.
				[b]Note:[/b] Always use [method remove_inspector_plugin] to remove the registered [EditorInspectorPlugin] when your [EditorPlugin] is disabled to prevent leaks and an unexpected behavior.
				[codeblocks]
				[gdscript]
				const MyInspectorPlugin = preload("res://addons/your_addon/path/to/your/script.gd")
				var inspector_plugin = MyInspectorPlugin.new()

				func _enter_tree():
				    add_inspector_plugin(inspector_plugin)

				func _exit_tree():
				    remove_inspector_plugin(inspector_plugin)
				[/gdscript]
				[/codeblocks]
			</description>
		</method>
		<method name="add_node_3d_gizmo_plugin">
			<return type="void" />
			<param index="0" name="plugin" type="EditorNode3DGizmoPlugin" />
			<description>
				Registers a new [EditorNode3DGizmoPlugin]. Gizmo plugins are used to add custom gizmos to the 3D preview viewport for a [Node3D].
				See [method add_inspector_plugin] for an example of how to register a plugin.
			</description>
		</method>
		<method name="add_resource_conversion_plugin">
			<return type="void" />
			<param index="0" name="plugin" type="EditorResourceConversionPlugin" />
			<description>
				Registers a new [EditorResourceConversionPlugin]. Resource conversion plugins are used to add custom resource converters to the editor inspector.
				See [EditorResourceConversionPlugin] for an example of how to create a resource conversion plugin.
			</description>
		</method>
		<method name="add_scene_format_importer_plugin">
			<return type="void" />
			<param index="0" name="scene_format_importer" type="EditorSceneFormatImporter" />
			<param index="1" name="first_priority" type="bool" default="false" />
			<description>
				Registers a new [EditorSceneFormatImporter]. Scene importers are used to import custom 3D asset formats as scenes.
				If [param first_priority] is [code]true[/code], the new import plugin is inserted first in the list and takes precedence over pre-existing plugins.
			</description>
		</method>
		<method name="add_scene_post_import_plugin">
			<return type="void" />
			<param index="0" name="scene_import_plugin" type="EditorScenePostImportPlugin" />
			<param index="1" name="first_priority" type="bool" default="false" />
			<description>
				Add a [EditorScenePostImportPlugin]. These plugins allow customizing the import process of 3D assets by adding new options to the import dialogs.
				If [param first_priority] is [code]true[/code], the new import plugin is inserted first in the list and takes precedence over pre-existing plugins.
			</description>
		</method>
		<method name="add_tool_menu_item">
			<return type="void" />
			<param index="0" name="name" type="String" />
			<param index="1" name="callable" type="Callable" />
			<description>
				Adds a custom menu item to [b]Project > Tools[/b] named [param name]. When clicked, the provided [param callable] will be called.
			</description>
		</method>
		<method name="add_tool_submenu_item">
			<return type="void" />
			<param index="0" name="name" type="String" />
			<param index="1" name="submenu" type="PopupMenu" />
			<description>
				Adds a custom [PopupMenu] submenu under [b]Project > Tools >[/b] [param name]. Use [method remove_tool_menu_item] on plugin clean up to remove the menu.
			</description>
		</method>
		<method name="add_translation_parser_plugin">
			<return type="void" />
			<param index="0" name="parser" type="EditorTranslationParserPlugin" />
			<description>
				Registers a custom translation parser plugin for extracting translatable strings from custom files.
			</description>
		</method>
		<method name="add_undo_redo_inspector_hook_callback">
			<return type="void" />
			<param index="0" name="callable" type="Callable" />
			<description>
				Hooks a callback into the undo/redo action creation when a property is modified in the inspector. This allows, for example, to save other properties that may be lost when a given property is modified.
				The callback should have 4 arguments: [Object] [code]undo_redo[/code], [Object] [code]modified_object[/code], [String] [code]property[/code] and [Variant] [code]new_value[/code]. They are, respectively, the [UndoRedo] object used by the inspector, the currently modified object, the name of the modified property and the new value the property is about to take.
			</description>
		</method>
		<method name="get_editor_interface" deprecated="[EditorInterface] is a global singleton and can be accessed directly by its name.">
			<return type="EditorInterface" />
			<description>
				Returns the [EditorInterface] singleton instance.
			</description>
		</method>
		<method name="get_export_as_menu">
			<return type="PopupMenu" />
			<description>
				Returns the [PopupMenu] under [b]Scene > Export As...[/b].
			</description>
		</method>
		<method name="get_plugin_version" qualifiers="const">
			<return type="String" />
			<description>
				Provide the version of the plugin declared in the [code]plugin.cfg[/code] config file.
			</description>
		</method>
		<method name="get_script_create_dialog">
			<return type="ScriptCreateDialog" />
			<description>
				Gets the Editor's dialog used for making scripts.
				[b]Note:[/b] Users can configure it before use.
				[b]Warning:[/b] Removing and freeing this node will render a part of the editor useless and may cause a crash.
			</description>
		</method>
		<


<method name="abs" qualifiers="const">
			<return type="Vector3" />
			<description>
				Returns a new vector with all components in absolute values (i.e. positive).
			</description>
		</method>
		<method name="angle_to" qualifiers="const">
			<return type="float" />
			<param index="0" name="to" type="Vector3" />
			<description>
				Returns the unsigned minimum angle to the given vector, in radians.
			</description>
		</method>
		<method name="bezier_derivative" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="control_1" type="Vector3" />
			<param index="1" name="control_2" type="Vector3" />
			<param index="2" name="end" type="Vector3" />
			<param index="3" name="t" type="float" />
			<description>
				Returns the derivative at the given [param t] on the [url=https://en.wikipedia.org/wiki/B%C3%A9zier_curve]Bézier curve[/url] defined by this vector and the given [param control_1], [param control_2], and [param end] points.
			</description>
		</method>
		<method name="bezier_interpolate" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="control_1" type="Vector3" />
			<param index="1" name="control_2" type="Vector3" />
			<param index="2" name="end" type="Vector3" />
			<param index="3" name="t" type="float" />
			<description>
				Returns the point at the given [param t] on the [url=https://en.wikipedia.org/wiki/B%C3%A9zier_curve]Bézier curve[/url] defined by this vector and the given [param control_1], [param control_2], and [param end] points.
			</description>
		</method>
		<method name="bounce" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="n" type="Vector3" />
			<description>
				Returns the vector "bounced off" from a plane defined by the given normal [param n].
				[b]Note:[/b] [method bounce] performs the operation that most engines and frameworks call [code skip-lint]reflect()[/code].
			</description>
		</method>
		<method name="ceil" qualifiers="const">
			<return type="Vector3" />
			<description>
				Returns a new vector with all components rounded up (towards positive infinity).
			</description>
		</method>
		<method name="clamp" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="min" type="Vector3" />
			<param index="1" name="max" type="Vector3" />
			<description>
				Returns a new vector with all components clamped between the components of [param min] and [param max], by running [method @GlobalScope.clamp] on each component.
			</description>
		</method>
		<method name="clampf" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="min" type="float" />
			<param index="1" name="max" type="float" />
			<description>
				Returns a new vector with all components clamped between [param min] and [param max], by running [method @GlobalScope.clamp] on each component.
			</description>
		</method>
		<method name="cross" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="with" type="Vector3" />
			<description>
				Returns the cross product of this vector and [param with].
				This returns a vector perpendicular to both this and [param with], which would be the normal vector of the plane defined by the two vectors. As there are two such vectors, in opposite directions, this method returns the vector defined by a right-handed coordinate system. If the two vectors are parallel this returns an empty vector, making it useful for testing if two vectors are parallel.
			</description>
		</method>
		<method name="cubic_interpolate" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="b" type="Vector3" />
			<param index="1" name="pre_a" type="Vector3" />
			<param index="2" name="post_b" type="Vector3" />
			<param index="3" name="weight" type="float" />
			<description>
				Performs a cubic interpolation between this vector and [param b] using [param pre_a] and [param post_b] as handles, and returns the result at position [param weight]. [param weight] is on the range of 0.0 to 1.0, representing the amount of interpolation.
			</description>
		</method>
		<method name="cubic_interpolate_in_time" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="b" type="Vector3" />
			<param index="1" name="pre_a" type="Vector3" />
			<param index="2" name="post_b" type="Vector3" />
			<param index="3" name="weight" type="float" />
			<param index="4" name="b_t" type="float" />
			<param index="5" name="pre_a_t" type="float" />
			<param index="6" name="post_b_t" type="float" />
			<description>
				Performs a cubic interpolation between this vector and [param b] using [param pre_a] and [param post_b] as handles, and returns the result at position [param weight]. [param weight] is on the range of 0.0 to 1.0, representing the amount of interpolation.
				It can perform smoother interpolation than [method cubic_interpolate] by the time values.
			</description>
		</method>
		<method name="direction_to" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="to" type="Vector3" />
			<description>
				Returns the normalized vector pointing from this vector to [param to]. This is equivalent to using [code](b - a).normalized()[/code].
			</description>
		</method>
		<method name="distance_squared_to" qualifiers="const">
			<return type="float" />
			<param index="0" name="to" type="Vector3" />
			<description>
				Returns the squared distance between this vector and [param to].
				This method runs faster than [method distance_to], so prefer it if you need to compare vectors or need the squared distance for some formula.
			</description>
		</method>
		<method name="distance_to" qualifiers="const">
			<return type="float" />
			<param index="0" name="to" type="Vector3" />
			<description>
				Returns the distance between this vector and [param to].
			</description>
		</method>
		<method name="dot" qualifiers="const">
			<return type="float" />
			<param index="0" name="with" type="Vector3" />
			<description>
				Returns the dot product of this vector and [param with]. This can be used to compare the angle between two vectors. For example, this can be used to determine whether an enemy is facing the player.
				The dot product will be [code]0[/code] for a right angle (90 degrees), greater than 0 for angles narrower than 90 degrees and lower than 0 for angles wider than 90 degrees.
				When using unit (normalized) vectors, the result will always be between [code]-1.0[/code] (180 degree angle) when the vectors are facing opposite directions, and [code]1.0[/code] (0 degree angle) when the vectors are aligned.
				[b]Note:[/b] [code]a.dot(b)[/code] is equivalent to [code]b.dot(a)[/code].
			</description>
		</method>
		<method name="floor" qualifiers="const">
			<return type="Vector3" />
			<description>
				Returns a new vector with all components rounded down (towards negative infinity).
			</description>
		</method>
		<m


ethod name="posmod" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="mod" type="float" />
			<description>
				Returns a vector composed of the [method @GlobalScope.fposmod] of this vector's components and [param mod].
			</description>
		</method>
		<method name="posmodv" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="modv" type="Vector3" />
			<description>
				Returns a vector composed of the [method @GlobalScope.fposmod] of this vector's components and [param modv]'s components.
			</description>
		</method>
		<method name="project" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="b" type="Vector3" />
			<description>
				Returns a new vector resulting from projecting this vector onto the given vector [param b]. The resulting new vector is parallel to [param b]. See also [method slide].
				[b]Note:[/b] If the vector [param b] is a zero vector, the components of the resulting new vector will be [constant @GDScript.NAN].
			</description>
		</method>
		<method name="reflect" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="n" type="Vector3" />
			<description>
				Returns the result of reflecting the vector through a plane defined by the given normal vector [param n].
				[b]Note:[/b] [method reflect] differs from what other engines and frameworks call [code skip-lint]reflect()[/code]. In other engines, [code skip-lint]reflect()[/code] returns the result of the vector reflected by the given plane. The reflection thus passes through the given normal. While in Godot the reflection passes through the plane and can be thought of as bouncing off the normal. See also [method bounce] which does what most engines call [code skip-lint]reflect()[/code].
			</description>
		</method>
		<method name="rotated" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="axis" type="Vector3" />
			<param index="1" name="angle" type="float" />
			<description>
				Returns the result of rotating this vector around a given axis by [param angle] (in radians). The axis must be a normalized vector. See also [method @GlobalScope.deg_to_rad].
			</description>
		</method>
		<method name="round" qualifiers="const">
			<return type="Vector3" />
			<description>
				Returns a new vector with all components rounded to the nearest integer, with halfway cases rounded away from zero.
			</description>
		</method>
		<method name="sign" qualifiers="const">
			<return type="Vector3" />
			<description>
				Returns a new vector with each component set to [code]1.0[/code] if it's positive, [code]-1.0[/code] if it's negative, and [code]0.0[/code] if it's zero. The result is identical to calling [method @GlobalScope.sign] on each component.
			</description>
		</method>
		<method name="signed_angle_to" qualifiers="const">
			<return type="float" />
			<param index="0" name="to" type="Vector3" />
			<param index="1" name="axis" type="Vector3" />
			<description>
				Returns the signed angle to the given vector, in radians. The sign of the angle is positive in a counter-clockwise direction and negative in a clockwise direction when viewed from the side specified by the [param axis].
			</description>
		</method>
		<method name="slerp" qualifiers="const" keywords="interpolate">
			<return type="Vector3" />
			<param index="0" name="to" type="Vector3" />
			<param index="1" name="weight" type="float" />
			<description>
				Returns the result of spherical linear interpolation between this vector and [param to], by amount [param weight]. [param weight] is on the range of 0.0 to 1.0, representing the amount of interpolation.
				This method also handles interpolating the lengths if the input vectors have different lengths. For the special case of one or both input vectors having zero length, this method behaves like [method lerp].
			</description>
		</method>
		<method name="slide" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="n" type="Vector3" />
			<description>
				Returns a new vector resulting from sliding this vector along a plane with normal [param n]. The resulting new vector is perpendicular to [param n], and is equivalent to this vector minus its projection on [param n]. See also [method project].
				[b]Note:[/b] The vector [param n] must be normalized. See also [method normalized].
			</description>
		</method>
		<method name="snapped" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="step" type="Vector3" />
			<description>
				Returns a new vector with each component snapped to the nearest multiple of the corresponding component in [param step]. This can also be used to round the components to an arbitrary number of decimals.
			</description>
		</method>
		<method name="snappedf" qualifiers="const">
			<return type="Vector3" />
			<param index="0" name="step" type="float" />
			<description>
				Returns a new vector with each component snapped to the nearest multiple of [param step]. This can also be used to round the components to an arbitrary number of decimals.
			</description>
		</method>
	</methods>
	<members>
		<member name="x" type="float" setter="" getter="" default="0.0">
			The vector's X component. Also accessible by using the index position [code][0][/code].
		</member>
		<member name="y" type="float" setter="" getter="" default="0.0">
			The vector's Y component. Also accessible by using the index position [code][1][/code].
		</member>
		<member name="z" type="float" setter="" getter="" default="0.0">
			The vector's Z component. Also accessible by using the index position [code][2][/code].
		</member>
	</members>
	<c


methods>
		<method name="adjust_bcs">
			<return type="void" />
			<param index="0" name="brightness" type="float" />
			<param index="1" name="contrast" type="float" />
			<param index="2" name="saturation" type="float" />
			<description>
				Adjusts this image's [param brightness], [param contrast], and [param saturation] by the given values. Does not work if the image is compressed (see [method is_compressed]).
			</description>
		</method>
		<method name="blend_rect">
			<return type="void" />
			<param index="0" name="src" type="Image" />
			<param index="1" name="src_rect" type="Rect2i" />
			<param index="2" name="dst" type="Vector2i" />
			<description>
				Alpha-blends [param src_rect] from [param src] image to this image at coordinates [param dst], clipped accordingly to both image bounds. This image and [param src] image [b]must[/b] have the same format. [param src_rect] with non-positive size is treated as empty.
			</description>
		</method>
		<method name="blend_rect_mask">
			<return type="void" />
			<param index="0" name="src" type="Image" />
			<param index="1" name="mask" type="Image" />
			<param index="2" name="src_rect" type="Rect2i" />
			<param index="3" name="dst" type="Vector2i" />
			<description>
				Alpha-blends [param src_rect] from [param src] image to this image using [param mask] image at coordinates [param dst], clipped accordingly to both image bounds. Alpha channels are required for both [param src] and [param mask]. [param dst] pixels and [param src] pixels will blend if the corresponding mask pixel's alpha value is not 0. This image and [param src] image [b]must[/b] have the same format. [param src] image and [param mask] image [b]must[/b] have the same size (width and height) but they can have different formats. [param src_rect] with non-positive size is treated as empty.
			</description>
		</method>
		<method name="blit_rect">
			<return type="void" />
			<param index="0" name="src" type="Image" />
			<param index="1" name="src_rect" type="Rect2i" />
			<param index="2" name="dst" type="Vector2i" />
			<description>
				Copies [param src_rect] from [param src] image to this image at coordinates [param dst], clipped accordingly to both image bounds. This image and [param src] image [b]must[/b] have the same format. [param src_rect] with non-positive size is treated as empty.
			</description>
		</method>
		<method name="blit_rect_mask">
			<return type="void" />
			<param index="0" name="src" type="Image" />
			<param index="1" name="mask" type="Image" />
			<param index="2" name="src_rect" type="Rect2i" />
			<param index="3" name="dst" type="Vector2i" />
			<description>
				Blits [param src_rect] area from [param src] image to this image at the coordinates given by [param dst], clipped accordingly to both image bounds. [param src] pixel is copied onto [param dst] if the corresponding [param mask] pixel's alpha value is not 0. This image and [param src] image [b]must[/b] have the same format. [param src] image and [param mask] image [b]must[/b] have the same size (width and height) but they can have different formats. [param src_rect] with non-positive size is treated as empty.
			</description>
		</method>
		<method name="bump_map_to_normal_map">
			<return type="void" />
			<param index="0" name="bump_scale" type="float" default="1.0" />
			<description>
				Converts a bump map to a normal map. A bump map provides a height offset per-pixel, while a normal map provides a normal direction per pixel.
			</description>
		</method>
		<method name="clear_mipmaps">
			<return type="void" />
			<description>
				Removes the image's mipmaps.
			</description>
		</method>
		<method name="compress">
			<return type="int" enum="Error" />
			<param index="0" name="mode" type="int" enum="Image.CompressMode" />
			<param index="1" name="source" type="int" enum="Image.CompressSource" default="0" />
			<param index="2" name="astc_format" type="int" enum="Image.ASTCFormat" default="0" />
			<description>
				Compresses the image to use less memory. Can not directly access pixel data while the image is compressed. Returns error if the chosen compression mode is not available.
				The [param source] parameter helps to pick the best compression method for DXT and ETC2 formats. It is ignored for ASTC compression.
				For ASTC compression, the [param astc_format] parameter must be supplied.
			</description>
		</method>
		<method name="compress_from_channels">
			<return type="int" enum="Error" />
			<param index="0" name="mode" type="int" enum="Image.CompressMode" />
			<param index="1" name="channels" type="int" enum="Image.UsedChannels" />
			<param index="2" name="astc_format" type="int" enum="Image.ASTCFormat" default="0" />
			<description>
				Compresses the image to use less memory. Can not directly access pixel data while the image is compressed. Returns error if the chosen compression mode is not available.
				This is an alternative to [method compress] that lets the user supply the channels used in order for the compressor to pick the best DXT and ETC2 formats. For other formats (non DXT or ETC2), this argument is ignored.
				For ASTC compression, the [param astc_format] parameter must be supplied.
			</description>
		</method>
		<method name="compute_image_metrics">
			<return type="Dictionary" />
			<param index="0" name="compared_image" type="Image" />
			<param index="1" name="use_luma" type="bool" />
			<description>
				Compute image metrics on the current image and the compared image.
				The dictionary contains [code]max[/code], [code]mean[/code], [code]mean_squared[/code], [code]root_mean_squared[/code] and [code]peak_snr[/code].
			</description>
		</method>
		<method name="convert">
			<return type="void" />
			<param index="0" name="format" type="int" enum="Image.Format" />
			<description>
				Converts the image's format. See [enum Format] constants.
			</description>
		</method>
		<method name="copy_from">
			<return type="void" />
			<param index="0" name="src" type="Image" />
			<description>
				Copies [param src] image to this image.
			</description>
		</method>
		<method name="create" qualifiers="static" deprecated="Use [method create_empty].">
			<return type="Image" />
			<param index="0" name="width" type="int" />
			<param index="1" name="height" type="int" />
			<param index="2" name="use_mipmaps" type="bool" />
			<param index="3" name="format" type="int" enum="Image.Format" />
			<description>
				Creates an empty image of given size and format. See [enum Format] constants. If [param use_mipmaps] is [code]true[/code], then generate mipmaps for this image. See the [method generate_mipmaps].
			</description>
		</method>
		<


<?xml version="1.0" encoding="UTF-8" ?>
<class name="PackedScene" inherits="Resource" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../class.xsd">
	<brief_description>
		An abstraction of a serialized scene.
	</brief_description>
	<description>
		A simplified interface to a scene file. Provides access to operations and checks that can be performed on the scene resource itself.
		Can be used to save a node to a file. When saving, the node as well as all the nodes it owns get saved (see [member Node.owner] property).
		[b]Note:[/b] The node doesn't need to own itself.
		[b]Example of loading a saved scene:[/b]
		[codeblocks]
		[gdscript]
		# Use load() instead of preload() if the path isn't known at compile-time.
		var scene = preload("res://scene.tscn").instantiate()
		# Add the node as a child of the node the script is attached to.
		add_child(scene)
		[/gdscript]
		[csharp]
		// C# has no preload, so you have to always use ResourceLoader.Load<PackedScene>().
		var scene = ResourceLoader.Load<PackedScene>("res://scene.tscn").Instantiate();
		// Add the node as a child of the node the script is attached to.
		AddChild(scene);
		[/csharp]
		[/codeblocks]
		[b]Example of saving a node with different owners:[/b] The following example creates 3 objects: [Node2D] ([code]node[/code]), [RigidBody2D] ([code]body[/code]) and [CollisionObject2D] ([code]collision[/code]). [code]collision[/code] is a child of [code]body[/code] which is a child of [code]node[/code]. Only [code]body[/code] is owned by [code]node[/code] and [method pack] will therefore only save those two nodes, but not [code]collision[/code].
		[codeblocks]
		[gdscript]
		# Create the objects.
		var node = Node2D.new()
		var body = RigidBody2D.new()
		var collision = CollisionShape2D.new()

		# Create the object hierarchy.
		body.add_child(collision)
		node.add_child(body)

		# Change owner of `body`, but not of `collision`.
		body.owner = node
		var scene = PackedScene.new()

		# Only `node` and `body` are now packed.
		var result = scene.pack(node)
		if result == OK:
		    var error = ResourceSaver.save(scene, "res://path/name.tscn")  # Or "user://..."
		    if error != OK:
		        push_error("An error occurred while saving the scene to disk.")
		[/gdscript]
		[csharp]
		// Create the objects.
		var node = new Node2D();
		var body = new RigidBody2D();
		var collision = new CollisionShape2D();

		// Create the object hierarchy.
		body.AddChild(collision);
		node.AddChild(body);

		// Change owner of `body`, but not of `collision`.
		body.Owner = node;
		var scene = new PackedScene();

		// Only `node` and `body` are now packed.
		Error result = scene.Pack(node);
		if (result == Error.Ok)
		{
		    Error error = ResourceSaver.Save(scene, "res://path/name.tscn"); // Or "user://..."
		    if (error != Error.Ok)
		    {
		        GD.PushError("An error occurred while saving the scene to disk.");
		    }
		}
		[/csharp]
		[/codeblocks]
	</description>
	<tutorials>
		<link title="2D Role Playing Game (RPG) Demo">https://godotengine.org/asset-library/asset/2729</link>
	</tutorials>
	<methods>
		<method name="can_instantiate" qualifiers="const">
			<return type="bool" />
			<description>
				Returns [code]true[/code] if the scene file has nodes.
			</description>
		</method>
		<method name="get_state" qualifiers="const">
			<return type="SceneState" />
			<description>
				Returns the [SceneState] representing the scene file contents.
			</description>
		</method>
		<method name="instantiate" qualifiers="const" keywords="create, make, spawn, new">
			<return type="Node" />
			<param index="0" name="edit_state" type="int" enum="PackedScene.GenEditState" default="0" />
			<description>
				Instantiates the scene's node hierarchy. Triggers child scene instantiation(s). Triggers a [constant Node.NOTIFICATION_SCENE_INSTANTIATED] notification on the root node.
			</description>
		</method>
		<method name="pack">
			<return type="int" enum="Error" />
			<param index="0" name="path" type="Node" />
			<description>
				Packs the [param path] node, and all owned sub-nodes, into this [PackedScene]. Any existing data will be cleared. See [member Node.owner].
			</description>
		</method>
	</methods>
	<constants>
		<constant name="GEN_EDIT_STATE_DISABLED" value="0" enum="GenEditState">
			If passed to [method instantiate], blocks edits to the scene state.
		</constant>
		<constant name="GEN_EDIT_STATE_INSTANCE" value="1" enum="GenEditState">
			If passed to [method instantiate], provides local scene resources to the local scene.
			[b]Note:[/b] Only available in editor builds.
		</constant>
		<constant name="GEN_EDIT_STATE_MAIN" value="2" enum="GenEditState">
			If passed to [method instantiate], provides local scene resources to the local scene. Only the main scene should receive the main edit state.
			[b]Note:[/b] Only available in editor builds.
		</constant>
		<constant name="GEN_EDIT_STATE_MAIN_INHERITED" value="3" enum="GenEditState">
			It's similar to [constant GEN_EDIT_STATE_MAIN], but for the case where the scene is being instantiated to be the base of another one.
			[b]Note:[/b] Only available in editor builds.
		</constant>
	</constants>
</class>


<?xml version="1.0" encoding="UTF-8" ?>
<class name="EditorFileSystem" inherits="Node" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../class.xsd">
	<brief_description>
		Resource filesystem, as the editor sees it.
	</brief_description>
	<description>
		This object holds information of all resources in the filesystem, their types, etc.
		[b]Note:[/b] This class shouldn't be instantiated directly. Instead, access the singleton using [method EditorInterface.get_resource_filesystem].
	</description>
	<tutorials>
	</tutorials>
	<methods>
		<method name="get_file_type" qualifiers="const">
			<return type="String" />
			<param index="0" name="path" type="String" />
			<description>
				Returns the resource type of the file, given the full path. This returns a string such as [code]"Resource"[/code] or [code]"GDScript"[/code], [i]not[/i] a file extension such as [code]".gd"[/code].
			</description>
		</method>
		<method name="get_filesystem">
			<return type="EditorFileSystemDirectory" />
			<description>
				Gets the root directory object.
			</description>
		</method>
		<method name="get_filesystem_path">
			<return type="EditorFileSystemDirectory" />
			<param index="0" name="path" type="String" />
			<description>
				Returns a view into the filesystem at [param path].
			</description>
		</method>
		<method name="get_scanning_progress" qualifiers="const">
			<return type="float" />
			<description>
				Returns the scan progress for 0 to 1 if the FS is being scanned.
			</description>
		</method>
		<method name="is_scanning" qualifiers="const">
			<return type="bool" />
			<description>
				Returns [code]true[/code] if the filesystem is being scanned.
			</description>
		</method>
		<method name="reimport_files">
			<return type="void" />
			<param index="0" name="files" type="PackedStringArray" />
			<description>
				Reimports a set of files. Call this if these files or their [code].import[/code] files were directly edited by script or an external program.
				If the file type changed or the file was newly created, use [method update_file] or [method scan].
				[b]Note:[/b] This function blocks until the import is finished. However, the main loop iteration, including timers and [method Node._process], will occur during the import process due to progress bar updates. Avoid calls to [method reimport_files] or [method scan] while an import is in progress.
			</description>
		</method>
		<method name="scan">
			<return type="void" />
			<description>
				Scan the filesystem for changes.
			</description>
		</method>
		<method name="scan_sources">
			<return type="void" />
			<description>
				Check if the source of any imported resource changed.
			</description>
		</method>
		<method name="update_file">
			<return type="void" />
			<param index="0" name="path" type="String" />
			<description>
				Add a file in an existing directory, or schedule file information to be updated on editor restart. Can be used to update text files saved by an external program.
				This will not import the file. To reimport, call [method reimport_files] or [method scan] methods.
			</description>
		</method>
	</methods>
	<signals>
		<signal name="filesystem_changed">
			<description>
				Emitted if the filesystem changed.
			</description>
		</signal>
		<signal name="resources_reimported">
			<param index="0" name="resources" type="PackedStringArray" />
			<description>
				Emitted if a resource is reimported.
			</description>
		</signal>
		<signal name="resources_reimporting">
			<param index="0" name="resources" type="PackedStringArray" />
			<description>
				Emitted before a resource is reimported.
			</description>
		</signal>
		<signal name="resources_reload">
			<param index="0" name="resources" type="PackedStringArray" />
			<description>
				Emitted if at least one resource is reloaded when the filesystem is scanned.
			</description>
		</signal>
		<signal name="script_classes_updated">
			<description>
				Emitted when the list of global script classes gets updated.
			</description>
		</signal>
		<signal name="sources_changed">
			<param index="0" name="exist" type="bool" />
			<description>
				Emitted if the source of any imported file changed.
			</description>
		</signal>
	</signals>
</class>


RotationEditMode get_rotation_edit_mode() const;

	void set_rotation_order(EulerOrder p_order);
	void set_rotation(const Vector3 &p_euler_rad);
	void set_rotation_degrees(const Vector3 &p_euler_degrees);
	void set_scale(const Vector3 &p_scale);

	void set_global_position(const Vector3 &p_position);
	void set_global_basis(const Basis &p_basis);
	void set_global_rotation(const Vector3 &p_euler_rad);
	void set_global_rotation_degrees(const Vector3 &p_euler_degrees);

	Vector3 get_position() const;

	EulerOrder get_rotation_order() const;
	Vector3 get_rotation() const;
	Vector3 get_rotation_degrees() const;
	Vector3 get_scale() const;

	Vector3 get_global_position() const;
	Basis get_global_basis() const;
	Vector3 get_global_rotation() const;
	Vector3 get_global_rotation_degrees() const;

	void set_transform(const Transform3D &p_transform);
	void set_basis(const Basis &p_basis);
	void set_quaternion(const Quaternion &p_quaternion);
	void set_global_transform(const Transform3D &p_transform);

	Transform3D get_transform() const;
	Basis get_basis() const;
	Quaternion get_quaternion() const;
	Transform3D get_global_transform() const;

	Transform3D get_global_transform_interpolated();
	bool update_client_physics_interpolation_data();

#ifdef TOOLS_ENABLED
	virtual Transform3D get_global_gizmo_transform() const;
	virtual Transform3D get_local_gizmo_transform() const;
	virtual void set_transform_gizmo_visible(bool p_enabled) { data.transform_gizmo_visible = p_enabled; };
	virtual bool is_transform_gizmo_visible() const { return data.transform_gizmo_visible; };
#endif
	virtual void reparent(Node *p_parent, bool p_keep_global_transform = true) override;

	void set_disable_gizmos(bool p_enabled);
	void update_gizmos();
	void set_subgizmo_selection(Ref<Node3DGizmo> p_gizmo, int p_id, Transform3D p_transform = Transform3D());
	void clear_subgizmo_selection();
	Vector<Ref<Node3DGizmo>> get_gizmos() const;
	TypedArray<Node3DGizmo> get_gizmos_bind() const;
	void add_gizmo(Ref<Node3DGizmo> p_gizmo);
	void remove_gizmo(Ref<Node3DGizmo> p_gizmo);
	void clear_gizmos();

	void set_as_top_level(bool p_enabled);
	void set_as_top_level_keep_local(bool p_enabled);
	bool is_set_as_top_level() const;

	void set_disable_scale(bool p_enabled);
	bool is_scale_disabled() const;

	_FORCE_INLINE_ bool is_inside_world() const { return data.inside_world; }

	Transform3D get_relative_transform(const Node *p_parent) const;

	void rotate(const Vector3 &p_axis, real_t p_angle);
	void rotate_x(real_t p_angle);
	void rotate_y(real_t p_angle);
	void rotate_z(real_t p_angle);
	void translate(const Vector3 &p_offset);
	void scale(const Vector3 &p_ratio);

	void rotate_object_local(const Vector3 &p_axis, real_t p_angle);
	void scale_object_local(const Vector3 &p_scale);
	void translate_object_local(const Vector3 &p_offset);

	void global_rotate(const Vector3 &p_axis, real_t p_angle);
	void global_scale(const Vector3 &p_scale);
	void global_translate(const Vector3 &p_offset);

	void look_at(const Vector3 &p_target, const Vector3 &p_up = Vector3(0, 1, 0), bool p_use_model_front = false);
	void look_at_from_position(const Vector3 &p_pos, const Vector3 &p_target, const Vector3 &p_up = Vector3(0, 1, 0), bool p_use_model_front = false);

	Vector3 to_local(Vector3 p_global) const;
	Vector3 to_global(Vector3 p_local) const;

	void set_notify_transform(bool p_enabled);
	bool is_transform_notification_enabled() const;

	void set_notify_local_transform(bool p_enabled);
	bool is_local_transform_notification_enabled() const;

	void orthonormalize();
	void set_identity();

	void set_visible(bool p_visible);
	void show();
	void hide();
	bool is_visible() const;
	bool is_visible_in_tree() const;

	void force_update_transform();

	void set_visibility_parent(const NodePath &p_path);
	NodePath get_visibility_parent() const;

	Node3D();
	~Node3D();
};

VARIANT_ENUM_CAST(Node3D::RotationEditMode)

#endif // NODE_3D_H


/**************************************************************************/
/*  character_body_3d.h                                                   */
/**************************************************************************/
/*                         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.                 */
/**************************************************************************/

#ifndef CHARACTER_BODY_3D_H
#define CHARACTER_BODY_3D_H

#include "scene/3d/physics/kinematic_collision_3d.h"
#include "scene/3d/physics/physics_body_3d.h"

class CharacterBody3D : public PhysicsBody3D {
	GDCLASS(CharacterBody3D, PhysicsBody3D);

public:
	enum MotionMode {
		MOTION_MODE_GROUNDED,
		MOTION_MODE_FLOATING,
	};
	enum PlatformOnLeave {
		PLATFORM_ON_LEAVE_ADD_VELOCITY,
		PLATFORM_ON_LEAVE_ADD_UPWARD_VELOCITY,
		PLATFORM_ON_LEAVE_DO_NOTHING,
	};
	bool move_and_slide();
	void apply_floor_snap();

	const Vector3 &get_velocity() const;
	void set_velocity(const Vector3 &p_velocity);

	bool is_on_floor() const;
	bool is_on_floor_only() const;
	bool is_on_wall() const;
	bool is_on_wall_only() const;
	bool is_on_ceiling() const;
	bool is_on_ceiling_only() const;
	const Vector3 &get_last_motion() const;
	Vector3 get_position_delta() const;
	const Vector3 &get_floor_normal() const;
	const Vector3 &get_wall_normal() const;
	const Vector3 &get_real_velocity() const;
	real_t get_floor_angle(const Vector3 &p_up_direction = Vector3(0.0, 1.0, 0.0)) const;
	const Vector3 &get_platform_velocity() const;
	const Vector3 &get_platform_angular_velocity() const;

	virtual Vector3 get_linear_velocity() const override;

	int get_slide_collision_count() const;
	PhysicsServer3D::MotionResult get_slide_collision(int p_bounce) const;

	void set_safe_margin(real_t p_margin);
	real_t get_safe_margin() const;

	bool is_floor_stop_on_slope_enabled() const;
	void set_floor_stop_on_slope_enabled(bool p_enabled);

	bool is_floor_constant_speed_enabled() const;
	void set_floor_constant_speed_enabled(bool p_enabled);

	bool is_floor_block_on_wall_enabled() const;
	void set_floor_block_on_wall_enabled(bool p_enabled);

	bool is_slide_on_ceiling_enabled() const;
	void set_slide_on_ceiling_enabled(bool p_enabled);

	int get_max_slides() const;
	void set_max_slides(int p_max_slides);

	real_t get_floor_max_angle() const;
	void set_floor_max_angle(real_t p_radians);

	real_t get_floor_snap_length();
	void set_floor_snap_length(real_t p_floor_snap_length);

	real_t get_wall_min_slide_angle() const;
	void set_wall_min_slide_angle(real_t p_radians);

	uint32_t get_platform_floor_layers() const;
	void set_platform_floor_layers(const uint32_t p_exclude_layer);

	uint32_t get_platform_wall_layers() const;
	void set_platform_wall_layers(const uint32_t p_exclude_layer);

	void set_motion_mode(MotionMode p_mode);
	MotionMode get_motion_mode() const;

	void set_platform_on_leave(PlatformOnLeave p_on_leave_velocity);
	PlatformOnLeave get_platform_on_leave() const;

	CharacterBody3D();

private:
	real_t margin = 0.001;
	MotionMode motion_mode = MOTION_MODE_GROUNDED;
	PlatformOnLeave platform_on_leave = PLATFORM_ON_LEAVE_ADD_VELOCITY;
	union CollisionState {
		uint32_t state = 0;
		struct {
			bool floor;
			bool wall;
			bool ceiling;
		};

		CollisionState() {
		}

		CollisionState(bool p_floor, bool p_wall, bool p_ceiling) {
			floor = p_floor;
			wall = p_wall;
			ceiling = p_ceiling;
		}
	};

	CollisionState collision_state;
	bool floor_constant_speed = false;
	bool floor_stop_on_slope = true;
	bool floor_block_on_wall = true;
	bool slide_on_ceiling = true;
	int max_slides = 6;
	int platform_layer = 0;
	RID platform_rid;
	ObjectID platform_object_id;
	uint32_t platform_floor_layers = UINT32_MAX;
	uint32_t platform_wall_layers = 0;
	real_t floor_snap_length = 0.1;
	real_t floor_max_angle = Math::deg_to_rad((real_t)45.0);
	real_t wall_min_slide_angle = Math::deg_to_rad((real_t)15.0);
	Vector3 up_direction = Vector3(0.0, 1.0, 0.0);
	Vector3 velocity;
	Vector3 floor_normal;
	Vector3 wall_normal;
	Vector3 ceiling_normal;
	Vector3 last_motion;
	Vector3 platform_velocity;
	Vector3 platform_angular_velocity;
	Vector3 platform_ceiling_velocity;
	Vector3 previous_position;
	Vector3 real_velocity;

	Vector<PhysicsServer3D::MotionResult> motion_results;
	Vector<Ref<KinematicCollision3D>> slide_colliders;

	void _move_and_slide_floating(double p_delta);
	void _move_and_slide_grounded(double p_delta, bool p_was_on_floor);

	Ref<KinematicCollision3D> _get_slide_collision(int p_bounce);
	Ref<KinematicCollision3D> _get_last_slide_collision();
	const Vector3 &get_up_direction() const;
	bool _on_floor_if_snapped(bool p_was_on_floor, bool p_vel_dir_facing_up);
	void set_up_direction(const Vector3 &p_up_direction);
	void _set_collision_direction(const PhysicsServer3D::MotionResult &p_result, CollisionState &r_state, CollisionState p_apply_state = CollisionState(true, true, true));
	void _set_platform_data(const PhysicsServer3D::MotionCollision &p_collision);
	void _snap_on_floor(bool p_was_on_floor, bool p_vel_dir_facing_up);

protected:
	void _notification(int p_what);
	static void _bind_methods();
	void _validate_property(PropertyInfo &p_property) const;
};

VARIANT_ENUM_CAST(CharacterBody3D::MotionMode);
VARIANT_ENUM_CAST(CharacterBody3D::PlatformOnLeave);

#endif // CHARACTER_BODY_3D_H


/**************************************************************************/
/*  collision_object_3d.h                                                 */
/**************************************************************************/
/*                         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.                 */
/**************************************************************************/

#ifndef COLLISION_OBJECT_3D_H
#define COLLISION_OBJECT_3D_H

#include "scene/3d/camera_3d.h"
#include "scene/3d/node_3d.h"

class CollisionObject3D : public Node3D {
	GDCLASS(CollisionObject3D, Node3D);

public:
	enum DisableMode {
		DISABLE_MODE_REMOVE,
		DISABLE_MODE_MAKE_STATIC,
		DISABLE_MODE_KEEP_ACTIVE,
	};

private:
	uint32_t collision_layer = 1;
	uint32_t collision_mask = 1;
	real_t collision_priority = 1.0;

	bool area = false;

	RID rid;
	uint32_t callback_lock = 0;

	DisableMode disable_mode = DISABLE_MODE_REMOVE;

	PhysicsServer3D::BodyMode body_mode = PhysicsServer3D::BODY_MODE_STATIC;

	struct ShapeData {
		ObjectID owner_id;
		Transform3D xform;
		struct ShapeBase {
			RID debug_shape;
			Ref<Shape3D> shape;
			int index = 0;
		};

		Vector<ShapeBase> shapes;
		bool disabled = false;
	};

	int total_subshapes = 0;

	RBMap<uint32_t, ShapeData> shapes;

	bool only_update_transform_changes = false; // This is used for sync to physics.

	bool capture_input_on_drag = false;
	bool ray_pickable = true;

	HashSet<uint32_t> debug_shapes_to_update;
	int debug_shapes_count = 0;
	Transform3D debug_shape_old_transform;

	void _update_pickable();

	bool _are_collision_shapes_visible();
	void _update_shape_data(uint32_t p_owner);
	void _shape_changed(const Ref<Shape3D> &p_shape);
	void _update_debug_shapes();
	void _clear_debug_shapes();

	void _apply_disabled();
	void _apply_enabled();

protected:
	CollisionObject3D(RID p_rid, bool p_area);

	_FORCE_INLINE_ void lock_callback() { callback_lock++; }
	_FORCE_INLINE_ void unlock_callback() {
		ERR_FAIL_COND(callback_lock == 0);
		callback_lock--;
	}

	void _notification(int p_what);
	static void _bind_methods();

	void _on_transform_changed();

	friend class Viewport;
	virtual void _input_event_call(Camera3D *p_camera, const Ref<InputEvent> &p_input_event, const Vector3 &p_pos, const Vector3 &p_normal, int p_shape);
	virtual void _mouse_enter();
	virtual void _mouse_exit();

	void set_body_mode(PhysicsServer3D::BodyMode p_mode);

	virtual void _space_changed(const RID &p_new_space);

	void set_only_update_transform_changes(bool p_enable);
	bool is_only_update_transform_changes_enabled() const;

	GDVIRTUAL5(_input_event, Camera3D *, Ref<InputEvent>, Vector3, Vector3, int)
	GDVIRTUAL0(_mouse_enter)
	GDVIRTUAL0(_mouse_exit)
public:
	void set_collision_layer(uint32_t p_layer);
	uint32_t get_collision_layer() const;

	void set_collision_mask(uint32_t p_mask);
	uint32_t get_collision_mask() const;

	void set_collision_layer_value(int p_layer_number, bool p_value);
	bool get_collision_layer_value(int p_layer_number) const;

	void set_collision_mask_value(int p_layer_number, bool p_value);
	bool get_collision_mask_value(int p_layer_number) const;

	void set_collision_priority(real_t p_priority);
	real_t get_collision_priority() const;

	void set_disable_mode(DisableMode p_mode);
	DisableMode get_disable_mode() const;

	uint32_t create_shape_owner(Object *p_owner);
	void remove_shape_owner(uint32_t owner);
	void get_shape_owners(List<uint32_t> *r_owners);
	PackedInt32Array _get_shape_owners();

	void shape_owner_set_transform(uint32_t p_owner, const Transform3D &p_transform);
	Transform3D shape_owner_get_transform(uint32_t p_owner) const;
	Object *shape_owner_get_owner(uint32_t p_owner) const;

	void shape_owner_set_disabled(uint32_t p_owner, bool p_disabled);
	bool is_shape_owner_disabled(uint32_t p_owner) const;

	void shape_owner_add_shape(uint32_t p_owner, const Ref<Shape3D> &p_shape);
	int shape_owner_get_shape_count(uint32_t p_owner) const;
	Ref<Shape3D> shape_owner_get_shape(uint32_t p_owner, int p_shape) const;
	int shape_owner_get_shape_index(uint32_t p_owner, int p_shape) const;

	void shape_owner_remove_shape(uint32_t p_owner, int p_shape);
	void shape_owner_clear_shapes(uint32_t p_owner);

	uint32_t shape_find_owner(int p_shape_index) const;

	void set_ray_pickable(bool p_ray_pickable);
	bool is_ray_pickable() const;

	void set_capture_input_on_drag(bool p_capture);
	bool get_capture_input_on_drag() const;

	_FORCE_INLINE_ RID get_rid() const { return rid; }

	PackedStringArray get_configuration_warnings() const override;

	CollisionObject3D();
	~CollisionObject3D();
};

VARIANT_ENUM_CAST(CollisionObject3D::DisableMode);

#endif // COLLISION_OBJECT_3D_H


/**************************************************************************/
/*  ray_cast_3d.h                                                         */
/**************************************************************************/
/*                         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.                 */
/**************************************************************************/

#ifndef RAY_CAST_3D_H
#define RAY_CAST_3D_H

#include "scene/3d/node_3d.h"

class CollisionObject3D;

class RayCast3D : public Node3D {
	GDCLASS(RayCast3D, Node3D);

	bool enabled = true;
	bool collided = false;
	ObjectID against;
	RID against_rid;
	int against_shape = 0;
	Vector3 collision_point;
	Vector3 collision_normal;
	int collision_face_index = -1;

	Vector3 target_position = Vector3(0, -1, 0);
	HashSet<RID> exclude;

	uint32_t collision_mask = 1;
	bool exclude_parent_body = true;

	Ref<Material> debug_material;
	Color debug_shape_custom_color = Color(0.0, 0.0, 0.0);
	int debug_shape_thickness = 2;
	Vector<Vector3> debug_shape_vertices;
	Vector<Vector3> debug_line_vertices;

	void _create_debug_shape();
	void _update_debug_shape();
	void _update_debug_shape_material(bool p_check_collision = false);
	void _update_debug_shape_vertices();
	void _clear_debug_shape();

	bool collide_with_areas = false;
	bool collide_with_bodies = true;

	bool hit_from_inside = false;
	bool hit_back_faces = true;

	RID debug_instance;
	Ref<ArrayMesh> debug_mesh;

protected:
	void _notification(int p_what);
	void _update_raycast_state();
	static void _bind_methods();

public:
	void set_collide_with_areas(bool p_enabled);
	bool is_collide_with_areas_enabled() const;

	void set_collide_with_bodies(bool p_enabled);
	bool is_collide_with_bodies_enabled() const;

	void set_hit_from_inside(bool p_enabled);
	bool is_hit_from_inside_enabled() const;

	void set_hit_back_faces(bool p_enabled);
	bool is_hit_back_faces_enabled() const;

	void set_enabled(bool p_enabled);
	bool is_enabled() const;

	void set_target_position(const Vector3 &p_point);
	Vector3 get_target_position() const;

	void set_collision_mask(uint32_t p_mask);
	uint32_t get_collision_mask() const;

	void set_collision_mask_value(int p_layer_number, bool p_value);
	bool get_collision_mask_value(int p_layer_number) const;

	void set_exclude_parent_body(bool p_exclude_parent_body);
	bool get_exclude_parent_body() const;

	const Color &get_debug_shape_custom_color() const;
	void set_debug_shape_custom_color(const Color &p_color);

	const Vector<Vector3> &get_debug_shape_vertices() const;
	const Vector<Vector3> &get_debug_line_vertices() const;

	Ref<StandardMaterial3D> get_debug_material();

	int get_debug_shape_thickness() const;
	void set_debug_shape_thickness(const int p_debug_thickness);

	void force_raycast_update();
	bool is_colliding() const;
	Object *get_collider() const;
	RID get_collider_rid() const;
	int get_collider_shape() const;
	Vector3 get_collision_point() const;
	Vector3 get_collision_normal() const;
	int get_collision_face_index() const;

	void add_exception_rid(const RID &p_rid);
	void add_exception(const CollisionObject3D *p_node);
	void remove_exception_rid(const RID &p_rid);
	void remove_exception(const CollisionObject3D *p_node);
	void clear_exceptions();

	RayCast3D();
};

#endif // RAY_CAST_3D_H


/**************************************************************************/
/*  sprite_frames.h                                                       */
/**************************************************************************/
/*                         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.                 */
/**************************************************************************/

#ifndef SPRITE_FRAMES_H
#define SPRITE_FRAMES_H

#include "scene/resources/texture.h"

static const float SPRITE_FRAME_MINIMUM_DURATION = 0.01;

class SpriteFrames : public Resource {
	GDCLASS(SpriteFrames, Resource);

	struct Frame {
		Ref<Texture2D> texture;
		float duration = 1.0;
	};

	struct Anim {
		double speed = 5.0;
		bool loop = true;
		Vector<Frame> frames;
	};

	HashMap<StringName, Anim> animations;

	Array _get_animations() const;
	void _set_animations(const Array &p_animations);

protected:
	static void _bind_methods();

public:
	void add_animation(const StringName &p_anim);
	bool has_animation(const StringName &p_anim) const;
	void duplicate_animation(const StringName &p_from, const StringName &p_to);
	void remove_animation(const StringName &p_anim);
	void rename_animation(const StringName &p_prev, const StringName &p_next);

	void get_animation_list(List<StringName> *r_animations) const;
	Vector<String> get_animation_names() const;

	void set_animation_speed(const StringName &p_anim, double p_fps);
	double get_animation_speed(const StringName &p_anim) const;

	void set_animation_loop(const StringName &p_anim, bool p_loop);
	bool get_animation_loop(const StringName &p_anim) const;

	void add_frame(const StringName &p_anim, const Ref<Texture2D> &p_texture, float p_duration = 1.0, int p_at_pos = -1);
	void set_frame(const StringName &p_anim, int p_idx, const Ref<Texture2D> &p_texture, float p_duration = 1.0);
	void remove_frame(const StringName &p_anim, int p_idx);

	int get_frame_count(const StringName &p_anim) const;

	_FORCE_INLINE_ Ref<Texture2D> get_frame_texture(const StringName &p_anim, int p_idx) const {
		HashMap<StringName, Anim>::ConstIterator E = animations.find(p_anim);
		ERR_FAIL_COND_V_MSG(!E, Ref<Texture2D>(), "Animation '" + String(p_anim) + "' doesn't exist.");
		ERR_FAIL_COND_V(p_idx < 0, Ref<Texture2D>());
		if (p_idx >= E->value.frames.size()) {
			return Ref<Texture2D>();
		}

		return E->value.frames[p_idx].texture;
	}

	_FORCE_INLINE_ float get_frame_duration(const StringName &p_anim, int p_idx) const {
		HashMap<StringName, Anim>::ConstIterator E = animations.find(p_anim);
		ERR_FAIL_COND_V_MSG(!E, 1.0, "Animation '" + String(p_anim) + "' doesn't exist.");
		ERR_FAIL_COND_V(p_idx < 0, 1.0);
		if (p_idx >= E->value.frames.size()) {
			return 1.0;
		}

		return E->value.frames[p_idx].duration;
	}

	void clear(const StringName &p_anim);
	void clear_all();

#ifdef TOOLS_ENABLED
	virtual void get_argument_options(const StringName &p_function, int p_idx, List<String> *r_options) const override;
#endif

	SpriteFrames();
};

#endif // SPRITE_FRAMES_H


/**************************************************************************/
/*  animation_blend_space_2d.h                                            */
/**************************************************************************/
/*                         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.                 */
/**************************************************************************/

#ifndef ANIMATION_BLEND_SPACE_2D_H
#define ANIMATION_BLEND_SPACE_2D_H

#include "scene/animation/animation_tree.h"

class AnimationNodeBlendSpace2D : public AnimationRootNode {
	GDCLASS(AnimationNodeBlendSpace2D, AnimationRootNode);

public:
	enum BlendMode {
		BLEND_MODE_INTERPOLATED,
		BLEND_MODE_DISCRETE,
		BLEND_MODE_DISCRETE_CARRY,
	};

protected:
	enum {
		MAX_BLEND_POINTS = 64
	};

	struct BlendPoint {
		StringName name;
		Ref<AnimationRootNode> node;
		Vector2 position;
	};

	BlendPoint blend_points[MAX_BLEND_POINTS];
	int blend_points_used = 0;

	struct BlendTriangle {
		int points[3] = {};
	};

	Vector<BlendTriangle> triangles;

	StringName blend_position = "blend_position";
	StringName closest = "closest";
	Vector2 max_space = Vector2(1, 1);
	Vector2 min_space = Vector2(-1, -1);
	Vector2 snap = Vector2(0.1, 0.1);
	String x_label = "x";
	String y_label = "y";
	BlendMode blend_mode = BLEND_MODE_INTERPOLATED;

	void _add_blend_point(int p_index, const Ref<AnimationRootNode> &p_node);
	void _set_triangles(const Vector<int> &p_triangles);
	Vector<int> _get_triangles() const;

	void _blend_triangle(const Vector2 &p_pos, const Vector2 *p_points, float *r_weights);

	bool auto_triangles = true;
	bool trianges_dirty = false;

	void _update_triangles();
	void _queue_auto_triangles();

	bool sync = false;

	void _validate_property(PropertyInfo &p_property) const;
	static void _bind_methods();

	virtual void _tree_changed() override;
	virtual void _animation_node_renamed(const ObjectID &p_oid, const String &p_old_name, const String &p_new_name) override;
	virtual void _animation_node_removed(const ObjectID &p_oid, const StringName &p_node) override;

public:
	virtual void get_parameter_list(List<PropertyInfo> *r_list) const override;
	virtual Variant get_parameter_default_value(const StringName &p_parameter) const override;

	virtual void get_child_nodes(List<ChildNode> *r_child_nodes) override;

	void add_blend_point(const Ref<AnimationRootNode> &p_node, const Vector2 &p_position, int p_at_index = -1);
	void set_blend_point_position(int p_point, const Vector2 &p_position);
	void set_blend_point_node(int p_point, const Ref<AnimationRootNode> &p_node);
	Vector2 get_blend_point_position(int p_point) const;
	Ref<AnimationRootNode> get_blend_point_node(int p_point) const;
	void remove_blend_point(int p_point);
	int get_blend_point_count() const;

	bool has_triangle(int p_x, int p_y, int p_z) const;
	void add_triangle(int p_x, int p_y, int p_z, int p_at_index = -1);
	int get_triangle_point(int p_triangle, int p_point);
	void remove_triangle(int p_triangle);
	int get_triangle_count() const;

	void set_min_space(const Vector2 &p_min);
	Vector2 get_min_space() const;

	void set_max_space(const Vector2 &p_max);
	Vector2 get_max_space() const;

	void set_snap(const Vector2 &p_snap);
	Vector2 get_snap() const;

	void set_x_label(const String &p_label);
	String get_x_label() const;

	void set_y_label(const String &p_label);
	String get_y_label() const;

	virtual NodeTimeInfo _process(const AnimationMixer::PlaybackInfo p_playback_info, bool p_test_only = false) override;
	virtual String get_caption() const override;

	Vector2 get_closest_point(const Vector2 &p_point);

	void set_auto_triangles(bool p_enable);
	bool get_auto_triangles() const;

	void set_blend_mode(BlendMode p_blend_mode);
	BlendMode get_blend_mode() const;

	void set_use_sync(bool p_sync);
	bool is_using_sync() const;

	virtual Ref<AnimationNode> get_child_by_name(const StringName &p_name) const override;

	AnimationNodeBlendSpace2D();
	~AnimationNodeBlendSpace2D();
};

VARIANT_ENUM_CAST(AnimationNodeBlendSpace2D::BlendMode)

#endif // ANIMATION_BLEND_SPACE_2D_H


class Control : public CanvasItem {
	GDCLASS(Control, CanvasItem);

#ifdef TOOLS_ENABLED
	bool saving = false;
#endif

public:
	enum Anchor {
		ANCHOR_BEGIN = 0,
		ANCHOR_END = 1
	};

	enum GrowDirection {
		GROW_DIRECTION_BEGIN,
		GROW_DIRECTION_END,
		GROW_DIRECTION_BOTH
	};

	enum FocusMode {
		FOCUS_NONE,
		FOCUS_CLICK,
		FOCUS_ALL
	};

	enum SizeFlags {
		SIZE_SHRINK_BEGIN = 0,
		SIZE_FILL = 1,
		SIZE_EXPAND = 2,
		SIZE_SHRINK_CENTER = 4,
		SIZE_SHRINK_END = 8,

		SIZE_EXPAND_FILL = SIZE_EXPAND | SIZE_FILL,
	};

	enum MouseFilter {
		MOUSE_FILTER_STOP,
		MOUSE_FILTER_PASS,
		MOUSE_FILTER_IGNORE
	};

	enum CursorShape {
		CURSOR_ARROW,
		CURSOR_IBEAM,
		CURSOR_POINTING_HAND,
		CURSOR_CROSS,
		CURSOR_WAIT,
		CURSOR_BUSY,
		CURSOR_DRAG,
		CURSOR_CAN_DROP,
		CURSOR_FORBIDDEN,
		CURSOR_VSIZE,
		CURSOR_HSIZE,
		CURSOR_BDIAGSIZE,
		CURSOR_FDIAGSIZE,
		CURSOR_MOVE,
		CURSOR_VSPLIT,
		CURSOR_HSPLIT,
		CURSOR_HELP,
		CURSOR_MAX
	};

	enum LayoutPreset {
		PRESET_TOP_LEFT,
		PRESET_TOP_RIGHT,
		PRESET_BOTTOM_LEFT,
		PRESET_BOTTOM_RIGHT,
		PRESET_CENTER_LEFT,
		PRESET_CENTER_TOP,
		PRESET_CENTER_RIGHT,
		PRESET_CENTER_BOTTOM,
		PRESET_CENTER,
		PRESET_LEFT_WIDE,
		PRESET_TOP_WIDE,
		PRESET_RIGHT_WIDE,
		PRESET_BOTTOM_WIDE,
		PRESET_VCENTER_WIDE,
		PRESET_HCENTER_WIDE,
		PRESET_FULL_RECT
	};

	enum LayoutPresetMode {
		PRESET_MODE_MINSIZE,
		PRESET_MODE_KEEP_WIDTH,
		PRESET_MODE_KEEP_HEIGHT,
		PRESET_MODE_KEEP_SIZE
	};

	enum LayoutMode {
		LAYOUT_MODE_POSITION,
		LAYOUT_MODE_ANCHORS,
		LAYOUT_MODE_CONTAINER,
		LAYOUT_MODE_UNCONTROLLED,
	};

	enum LayoutDirection {
		LAYOUT_DIRECTION_INHERITED,
		LAYOUT_DIRECTION_APPLICATION_LOCALE,
		LAYOUT_DIRECTION_LTR,
		LAYOUT_DIRECTION_RTL,
		LAYOUT_DIRECTION_SYSTEM_LOCALE,
		LAYOUT_DIRECTION_MAX,
#ifndef DISABLE_DEPRECATED
		LAYOUT_DIRECTION_LOCALE = LAYOUT_DIRECTION_APPLICATION_LOCALE,
#endif // DISABLE_DEPRECATED
	};

	enum TextDirection {
		TEXT_DIRECTION_AUTO = TextServer::DIRECTION_AUTO,
		TEXT_DIRECTION_LTR = TextServer::DIRECTION_LTR,
		TEXT_DIRECTION_RTL = TextServer::DIRECTION_RTL,
		TEXT_DIRECTION_INHERITED = TextServer::DIRECTION_INHERITED,
	};

private:
	struct CComparator {
		bool operator()(const Control *p_a, const Control *p_b) const {
			if (p_a->get_canvas_layer() == p_b->get_canvas_layer()) {
				return p_b->is_greater_than(p_a);
			}

			return p_a->get_canvas_layer() < p_b->get_canvas_layer();
		}
	};

	// This Data struct is to avoid namespace pollution in derived classes.
	struct Data {
		bool initialized = false;

		// Global relations.

		List<Control *>::Element *RI = nullptr;

		Control *parent_control = nullptr;
		Window *parent_window = nullptr;
		CanvasItem *parent_canvas_item = nullptr;
		Callable forward_drag;
		Callable forward_can_drop;
		Callable forward_drop;

		// Positioning and sizing.

		LayoutMode stored_layout_mode = LayoutMode::LAYOUT_MODE_POSITION;
		bool stored_use_custom_anchors = false;

		real_t offset[4] = { 0.0, 0.0, 0.0, 0.0 };
		real_t anchor[4] = { ANCHOR_BEGIN, ANCHOR_BEGIN, ANCHOR_BEGIN, ANCHOR_BEGIN };
		FocusMode focus_mode = FOCUS_NONE;
		GrowDirection h_grow = GROW_DIRECTION_END;
		GrowDirection v_grow = GROW_DIRECTION_END;

		real_t rotation = 0.0;
		Vector2 scale = Vector2(1, 1);
		Vector2 pivot_offset;

		Point2 pos_cache;
		Size2 size_cache;
		Size2 minimum_size_cache;
		bool minimum_size_valid = false;

		Size2 last_minimum_size;
		bool updating_last_minimum_size = false;
		bool block_minimum_size_adjust = false;

		bool size_warning = true;

		// Container sizing.

		BitField<SizeFlags> h_size_flags = SIZE_FILL;
		BitField<SizeFlags> v_size_flags = SIZE_FILL;
		real_t expand = 1.0;
		Point2 custom_minimum_size;

		// Input events and rendering.

		MouseFilter mouse_filter = MOUSE_FILTER_STOP;
		bool force_pass_scroll_events = true;

		bool clip_contents = false;
		bool disable_visibility_clip = false;

		CursorShape default_cursor = CURSOR_ARROW;

		// Focus.

		NodePath focus_neighbor[4];
		NodePath focus_next;
		NodePath focus_prev;

		ObjectID shortcut_context;

		// Theming.

		ThemeOwner *theme_owner = nullptr;
		Ref<Theme> theme;
		StringName theme_type_variation;

		bool bulk_theme_override = false;
		Theme::ThemeIconMap theme_icon_override;
		Theme::ThemeStyleMap theme_style_override;
		Theme::ThemeFontMap theme_font_override;
		Theme::ThemeFontSizeMap theme_font_size_override;
		Theme::ThemeColorMap theme_color_override;
		Theme::ThemeConstantMap theme_constant_override;

		mutable HashMap<StringName, Theme::ThemeIconMap> theme_icon_cache;
		mutable HashMap<StringName, Theme::ThemeStyleMap> theme_style_cache;
		mutable HashMap<StringName, Theme::ThemeFontMap> theme_font_cache;
		mutable HashMap<StringName, Theme::ThemeFontSizeMap> theme_font_size_cache;
		mutable HashMap<StringName, Theme::ThemeColorMap> theme_color_cache;
		mutable HashMap<StringName, Theme::ThemeConstantMap> theme_constant_cache;

		// Internationalization.

		LayoutDirection layout_dir = LAYOUT_DIRECTION_INHERITED;
		bool is_rtl_dirty = true;
		bool is_rtl = false;

		bool localize_numeral_system = true;

		// Extra properties.

		String tooltip;
		AutoTranslateMode tooltip_auto_translate_mode = AUTO_TRANSLATE_MODE_INHERIT;

	} data;

	// Dynamic properties.

	static constexpr unsigned properties_managed_by_container_count = 12;
	static String properties_managed_by_container[properties_managed_by_container_count];

	// Global relations.

	friend class Viewport;

	// Positioning and sizing.

	void _update_canvas_item_transform();
	Transform2D _get_internal_transform() const;

	void _set_anchor(Side p_side, real_t p_anchor);
	void _set_position(const Point2 &p_point);
	void _set_global_position(const Point2 &p_point);
	void _set_size(const Size2 &p_size);

	void _compute_offsets(Rect2 p_rect, const real_t p_anchors[4], real_t (&r_offsets)[4]);
	void _compute_anchors(Rect2 p_rect, const real_t p_offsets[4], real_t (&r_anchors)[4]);

	void _set_layout_mode(LayoutMode p_mode);
	void _update_layout_mode();
	LayoutMode _get_layout_mode() const;
	LayoutMode _get_default_layout_mode() const;
	void _set_anchors_layout_preset(int p_preset);
	int _get_anchors_layout_preset() const;

	void _update_minimum_size_cache();
	void _update_minimum_size();
	void _size_changed();

	void _top_level_changed() override {} // Controls don't need to do anything, only other CanvasItems.
	void _top_level_changed_on_parent() override;

	void _clear_size_warning();

	// Input events.

	void _call_gui_input(const Ref<InputEvent> &p_event);

	// Focus.

	void _window_find_focus_neighbor(const Vector2 &p_dir, Node *p_at, const Point2 *p_points, real_t p_min, real_t &r_closest_dist, Control **r_closest);
	Control *_get_focus_neighbor(Side p_side, int p_count = 0);

	// Theming.

	void _theme_changed();
	void _notify_theme_override_changed();
	void _invalidate_theme_cache();

	// Extra properties.

	static int root_layout_direction;

	String get_tooltip_text() const;

protected:
	// Dynamic properties.

	bool _set(const StringName &p_name, const Variant &p_value);
	bool _get(const StringName &p_name, Variant &r_ret) const;
	void _get_property_list(List<PropertyInfo> *p_list) const;
	void _validate_property(PropertyInfo &p_property) const;

	bool _property_can_revert(const StringName &p_name) const;


bool _property_get_revert(const StringName &p_name, Variant &r_property) const;

	// Theming.

	virtual void _update_theme_item_cache();

	// Internationalization.

	virtual TypedArray<Vector3i> structured_text_parser(TextServer::StructuredTextParser p_parser_type, const Array &p_args, const String &p_text) const;

	// Base object overrides.

	void _notification(int p_notification);
	static void _bind_methods();

	// Exposed virtual methods.

	GDVIRTUAL1RC(bool, _has_point, Vector2)
	GDVIRTUAL2RC(TypedArray<Vector3i>, _structured_text_parser, Array, String)
	GDVIRTUAL0RC(Vector2, _get_minimum_size)
	GDVIRTUAL1RC(String, _get_tooltip, Vector2)

	GDVIRTUAL1R(Variant, _get_drag_data, Vector2)
	GDVIRTUAL2RC(bool, _can_drop_data, Vector2, Variant)
	GDVIRTUAL2(_drop_data, Vector2, Variant)
	GDVIRTUAL1RC(Object *, _make_custom_tooltip, String)

	GDVIRTUAL1(_gui_input, Ref<InputEvent>)

public:
	enum {
		NOTIFICATION_RESIZED = 40,
		NOTIFICATION_MOUSE_ENTER = 41,
		NOTIFICATION_MOUSE_EXIT = 42,
		NOTIFICATION_FOCUS_ENTER = 43,
		NOTIFICATION_FOCUS_EXIT = 44,
		NOTIFICATION_THEME_CHANGED = 45,
		NOTIFICATION_SCROLL_BEGIN = 47,
		NOTIFICATION_SCROLL_END = 48,
		NOTIFICATION_LAYOUT_DIRECTION_CHANGED = 49,
		NOTIFICATION_MOUSE_ENTER_SELF = 60,
		NOTIFICATION_MOUSE_EXIT_SELF = 61,
	};

	// Editor plugin interoperability.

	// TODO: Decouple controls from their editor plugin and get rid of this.
#ifdef TOOLS_ENABLED
	virtual Dictionary _edit_get_state() const override;
	virtual void _edit_set_state(const Dictionary &p_state) override;

	virtual void _edit_set_position(const Point2 &p_position) override;
	virtual Point2 _edit_get_position() const override;

	virtual void _edit_set_scale(const Size2 &p_scale) override;
	virtual Size2 _edit_get_scale() const override;

	virtual void _edit_set_rect(const Rect2 &p_edit_rect) override;
	virtual Rect2 _edit_get_rect() const override;
	virtual bool _edit_use_rect() const override;

	virtual void _edit_set_rotation(real_t p_rotation) override;
	virtual real_t _edit_get_rotation() const override;
	virtual bool _edit_use_rotation() const override;

	virtual void _edit_set_pivot(const Point2 &p_pivot) override;
	virtual Point2 _edit_get_pivot() const override;
	virtual bool _edit_use_pivot() const override;

	virtual Size2 _edit_get_minimum_size() const override;
#endif
	virtual void reparent(Node *p_parent, bool p_keep_global_transform = true) override;

	// Editor integration.

	static void set_root_layout_direction(int p_root_dir);

	PackedStringArray get_configuration_warnings() const override;
#ifdef TOOLS_ENABLED
	virtual void get_argument_options(const StringName &p_function, int p_idx, List<String> *r_options) const override;
#endif

	virtual bool is_text_field() const;

	// Global relations.

	bool is_top_level_control() const;

	Control *get_parent_control() const;
	Window *get_parent_window() const;
	Control *get_root_parent_control() const;

	Size2 get_parent_area_size() const;
	Rect2 get_parent_anchorable_rect() const;

	// Positioning and sizing.

	virtual Transform2D get_transform() const override;

	void set_anchor(Side p_side, real_t p_anchor, bool p_keep_offset = true, bool p_push_opposite_anchor = true);
	real_t get_anchor(Side p_side) const;
	void set_offset(Side p_side, real_t p_value);
	real_t get_offset(Side p_side) const;
	void set_anchor_and_offset(Side p_side, real_t p_anchor, real_t p_pos, bool p_push_opposite_anchor = true);

	// TODO: Rename to set_begin/end_offsets ?
	void set_begin(const Point2 &p_point);
	Point2 get_begin() const;
	void set_end(const Point2 &p_point);
	Point2 get_end() const;

	void set_h_grow_direction(GrowDirection p_direction);
	GrowDirection get_h_grow_direction() const;
	void set_v_grow_direction(GrowDirection p_direction);
	GrowDirection get_v_grow_direction() const;

	void set_anchors_preset(LayoutPreset p_preset, bool p_keep_offsets = true);
	void set_offsets_preset(LayoutPreset p_preset, LayoutPresetMode p_resize_mode = PRESET_MODE_MINSIZE, int p_margin = 0);
	void set_anchors_and_offsets_preset(LayoutPreset p_preset, LayoutPresetMode p_resize_mode = PRESET_MODE_MINSIZE, int p_margin = 0);
	void set_grow_direction_preset(LayoutPreset p_preset);

	void set_position(const Point2 &p_point, bool p_keep_offsets = false);
	void set_global_position(const Point2 &p_point, bool p_keep_offsets = false);
	Point2 get_position() const;
	Point2 get_global_position() const;
	Point2 get_screen_position() const;

	void set_size(const Size2 &p_size, bool p_keep_offsets = false);
	Size2 get_size() const;
	void reset_size();

	void set_rect(const Rect2 &p_rect); // Reset anchors to begin and set rect, for faster container children sorting.
	Rect2 get_rect() const;
	Rect2 get_global_rect() const;
	Rect2 get_screen_rect() const;
	Rect2 get_anchorable_rect() const override;

	void set_scale(const Vector2 &p_scale);
	Vector2 get_scale() const;
	void set_rotation(real_t p_radians);
	void set_rotation_degrees(real_t p_degrees);
	real_t get_rotation() const;
	real_t get_rotation_degrees() const;
	void set_pivot_offset(const Vector2 &p_pivot);
	Vector2 get_pivot_offset() const;

	void update_minimum_size();

	void set_block_minimum_size_adjust(bool p_block);

	virtual Size2 get_minimum_size() const;
	virtual Size2 get_combined_minimum_size() const;

	void set_custom_minimum_size(const Size2 &p_custom);
	Size2 get_custom_minimum_size() const;

	// Container sizing.

	void set_h_size_flags(BitField<SizeFlags> p_flags);
	BitField<SizeFlags> get_h_size_flags() const;
	void set_v_size_flags(BitField<SizeFlags> p_flags);
	BitField<SizeFlags> get_v_size_flags() const;
	void set_stretch_ratio(real_t p_ratio);
	real_t get_stretch_ratio() const;

	// Input events.

	virtual void gui_input(const Ref<InputEvent> &p_event);
	void accept_event();

	virtual bool has_point(const Point2 &p_point) const;

	void set_mouse_filter(MouseFilter p_filter);
	MouseFilter get_mouse_filter() const;

	void set_force_pass_scroll_events(bool p_force_pass_scroll_events);
	bool is_force_pass_scroll_events() const;

	void warp_mouse(const Point2 &p_position);

	bool is_focus_owner_in_shortcut_context() const;
	void set_shortcut_context(const Node *p_node);
	Node *get_shortcut_context() const;

	// Drag and drop handling.

	virtual void set_drag_forwarding(const Callable &p_drag, const Callable &p_can_drop, const Callable &p_drop);
	virtual Variant get_drag_data(const Point2 &p_point);
	virtual bool can_drop_data(const Point2 &p_point, const Variant &p_data) const;
	virtual void drop_data(const Point2 &p_point, const Variant &p_data);
	void set_drag_preview(Control *p_control);
	void force_drag(const Variant &p_data, Control *p_control);
	bool is_drag_successful() const;

	// Focus.

	void set_focus_mode(FocusMode p_focus_mode);
	FocusMode get_focus_mode() const;
	bool has_focus() const;
	void grab_focus();
	void grab_click_focus();
	void release_focus();

	Control *find_next_valid_focus() const;
	Control *find_prev_valid_focus() const;
	Control *find_valid_focus_neighbor(Side p_size) const;

	void set_focus_neighbor(Side p_side, const NodePath &p_neighbor);
	NodePath get_focus_neighbor(Side p_side) const;

	void set_focus_next(const NodePath &p_next);
	NodePath get_focus_next() const;
	void set_focus_previous(const NodePath &p_prev);
	NodePath get_focus_previous() const;

	// Rendering.

	void set_default_cursor_shape(CursorShape p_shape);
	CursorShape get_default_cursor_shape() const;
	virtual CursorShape get_cursor_shape(const Point2 &p_pos = Point2i()) const;

	void set_clip_contents(bool p_clip);
	bool is_clipping_contents();

	void set_disable_visibility_clip(bool p_ignore);
	bool is_visibility_clip_disabled() const;

	// Theming.

	void set_theme_owner_node(Node *p_node);
	Node *get_theme_owner_node() const;
	bool has_theme_owner_node() const;

	void set_theme_context(ThemeContext *p_context, bool p_propagate = true);

	void set_theme(const Ref<Theme> &p_theme);
	Ref<Theme> get_theme() const;

	void set_theme_type_variation(const StringName &p_theme_type);
	StringName get_theme_type_variation() const;

	void begin_bulk_theme_override();
	void end_bulk_theme_override();

	void add_theme_icon_override(const StringName &p_name, const Ref<Texture2D> &p_icon);


void add_theme_style_override(const StringName &p_name, const Ref<StyleBox> &p_style);
	void add_theme_font_override(const StringName &p_name, const Ref<Font> &p_font);
	void add_theme_font_size_override(const StringName &p_name, int p_font_size);
	void add_theme_color_override(const StringName &p_name, const Color &p_color);
	void add_theme_constant_override(const StringName &p_name, int p_constant);

	void remove_theme_icon_override(const StringName &p_name);
	void remove_theme_style_override(const StringName &p_name);
	void remove_theme_font_override(const StringName &p_name);
	void remove_theme_font_size_override(const StringName &p_name);
	void remove_theme_color_override(const StringName &p_name);
	void remove_theme_constant_override(const StringName &p_name);

	Ref<Texture2D> get_theme_icon(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	Ref<StyleBox> get_theme_stylebox(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	Ref<Font> get_theme_font(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	int get_theme_font_size(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	Color get_theme_color(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	int get_theme_constant(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	Variant get_theme_item(Theme::DataType p_data_type, const StringName &p_name, const StringName &p_theme_type = StringName()) const;
#ifdef TOOLS_ENABLED
	Ref<Texture2D> get_editor_theme_icon(const StringName &p_name) const;
#endif

	bool has_theme_icon_override(const StringName &p_name) const;
	bool has_theme_stylebox_override(const StringName &p_name) const;
	bool has_theme_font_override(const StringName &p_name) const;
	bool has_theme_font_size_override(const StringName &p_name) const;
	bool has_theme_color_override(const StringName &p_name) const;
	bool has_theme_constant_override(const StringName &p_name) const;

	bool has_theme_icon(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	bool has_theme_stylebox(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	bool has_theme_font(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	bool has_theme_font_size(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	bool has_theme_color(const StringName &p_name, const StringName &p_theme_type = StringName()) const;
	bool has_theme_constant(const StringName &p_name, const StringName &p_theme_type = StringName()) const;

	float get_theme_default_base_scale() const;
	Ref<Font> get_theme_default_font() const;
	int get_theme_default_font_size() const;

	// Internationalization.

	void set_layout_direction(LayoutDirection p_direction);
	LayoutDirection get_layout_direction() const;
	virtual bool is_layout_rtl() const;

	void set_localize_numeral_system(bool p_enable);
	bool is_localizing_numeral_system() const;

#ifndef DISABLE_DEPRECATED
	void set_auto_translate(bool p_enable);
	bool is_auto_translating() const;
#endif

	void set_tooltip_auto_translate_mode(AutoTranslateMode p_mode);
	AutoTranslateMode get_tooltip_auto_translate_mode() const;

	// Extra properties.

	void set_tooltip_text(const String &text);
	virtual String get_tooltip(const Point2 &p_pos) const;
	virtual Control *make_custom_tooltip(const String &p_text) const;

	Control();
	~Control();
};

VARIANT_ENUM_CAST(Control::FocusMode);
VARIANT_BITFIELD_CAST(Control::SizeFlags);
VARIANT_ENUM_CAST(Control::CursorShape);
VARIANT_ENUM_CAST(Control::LayoutPreset);
VARIANT_ENUM_CAST(Control::LayoutPresetMode);
VARIANT_ENUM_CAST(Control::MouseFilter);
VARIANT_ENUM_CAST(Control::GrowDirection);
VARIANT_ENUM_CAST(Control::Anchor);
VARIANT_ENUM_CAST(Control::LayoutMode);
VARIANT_ENUM_CAST(Control::LayoutDirection);
VARIANT_ENUM_CAST(Control::TextDirection);

// G = get_drag_data_fw, C = can_drop_data_fw, D = drop_data_fw, U = underscore
#define SET_DRAG_FORWARDING_CD(from, to) from->set_drag_forwarding(Callable(), callable_mp(this, &to::can_drop_data_fw).bind(from), callable_mp(this, &to::drop_data_fw).bind(from));
#define SET_DRAG_FORWARDING_CDU(from, to) from->set_drag_forwarding(Callable(), callable_mp(this, &to::_can_drop_data_fw).bind(from), callable_mp(this, &to::_drop_data_fw).bind(from));
#define SET_DRAG_FORWARDING_GCD(from, to) from->set_drag_forwarding(callable_mp(this, &to::get_drag_data_fw).bind(from), callable_mp(this, &to::can_drop_data_fw).bind(from), callable_mp(this, &to::drop_data_fw).bind(from));
#define SET_DRAG_FORWARDING_GCDU(from, to) from->set_drag_forwarding(callable_mp(this, &to::_get_drag_data_fw).bind(from), callable_mp(this, &to::_can_drop_data_fw).bind(from), callable_mp(this, &to::_drop_data_fw).bind(from));

#endif // CONTROL_H


GDVIRTUAL0(_enter_tree)
	GDVIRTUAL0(_exit_tree)
	GDVIRTUAL0(_ready)
	GDVIRTUAL0RC(Vector<String>, _get_configuration_warnings)

	GDVIRTUAL1(_input, Ref<InputEvent>)
	GDVIRTUAL1(_shortcut_input, Ref<InputEvent>)
	GDVIRTUAL1(_unhandled_input, Ref<InputEvent>)
	GDVIRTUAL1(_unhandled_key_input, Ref<InputEvent>)

public:
	enum {
		// You can make your own, but don't use the same numbers as other notifications in other nodes.
		NOTIFICATION_ENTER_TREE = 10,
		NOTIFICATION_EXIT_TREE = 11,
		NOTIFICATION_MOVED_IN_PARENT = 12,
		NOTIFICATION_READY = 13,
		NOTIFICATION_PAUSED = 14,
		NOTIFICATION_UNPAUSED = 15,
		NOTIFICATION_PHYSICS_PROCESS = 16,
		NOTIFICATION_PROCESS = 17,
		NOTIFICATION_PARENTED = 18,
		NOTIFICATION_UNPARENTED = 19,
		NOTIFICATION_SCENE_INSTANTIATED = 20,
		NOTIFICATION_DRAG_BEGIN = 21,
		NOTIFICATION_DRAG_END = 22,
		NOTIFICATION_PATH_RENAMED = 23,
		NOTIFICATION_CHILD_ORDER_CHANGED = 24,
		NOTIFICATION_INTERNAL_PROCESS = 25,
		NOTIFICATION_INTERNAL_PHYSICS_PROCESS = 26,
		NOTIFICATION_POST_ENTER_TREE = 27,
		NOTIFICATION_DISABLED = 28,
		NOTIFICATION_ENABLED = 29,
		NOTIFICATION_RESET_PHYSICS_INTERPOLATION = 2001, // A GodotSpace Odyssey.
		// Keep these linked to Node.
		NOTIFICATION_WM_MOUSE_ENTER = 1002,
		NOTIFICATION_WM_MOUSE_EXIT = 1003,
		NOTIFICATION_WM_WINDOW_FOCUS_IN = 1004,
		NOTIFICATION_WM_WINDOW_FOCUS_OUT = 1005,
		NOTIFICATION_WM_CLOSE_REQUEST = 1006,
		NOTIFICATION_WM_GO_BACK_REQUEST = 1007,
		NOTIFICATION_WM_SIZE_CHANGED = 1008,
		NOTIFICATION_WM_DPI_CHANGE = 1009,
		NOTIFICATION_VP_MOUSE_ENTER = 1010,
		NOTIFICATION_VP_MOUSE_EXIT = 1011,

		NOTIFICATION_OS_MEMORY_WARNING = MainLoop::NOTIFICATION_OS_MEMORY_WARNING,
		NOTIFICATION_TRANSLATION_CHANGED = MainLoop::NOTIFICATION_TRANSLATION_CHANGED,
		NOTIFICATION_WM_ABOUT = MainLoop::NOTIFICATION_WM_ABOUT,
		NOTIFICATION_CRASH = MainLoop::NOTIFICATION_CRASH,
		NOTIFICATION_OS_IME_UPDATE = MainLoop::NOTIFICATION_OS_IME_UPDATE,
		NOTIFICATION_APPLICATION_RESUMED = MainLoop::NOTIFICATION_APPLICATION_RESUMED,
		NOTIFICATION_APPLICATION_PAUSED = MainLoop::NOTIFICATION_APPLICATION_PAUSED,
		NOTIFICATION_APPLICATION_FOCUS_IN = MainLoop::NOTIFICATION_APPLICATION_FOCUS_IN,
		NOTIFICATION_APPLICATION_FOCUS_OUT = MainLoop::NOTIFICATION_APPLICATION_FOCUS_OUT,
		NOTIFICATION_TEXT_SERVER_CHANGED = MainLoop::NOTIFICATION_TEXT_SERVER_CHANGED,

		// Editor specific node notifications
		NOTIFICATION_EDITOR_PRE_SAVE = 9001,
		NOTIFICATION_EDITOR_POST_SAVE = 9002,
	};

	/* NODE/TREE */

	StringName get_name() const;
	String get_description() const;
	void set_name(const String &p_name);

	InternalMode get_internal_mode() const;

	void add_child(Node *p_child, bool p_force_readable_name = false, InternalMode p_internal = INTERNAL_MODE_DISABLED);
	void add_sibling(Node *p_sibling, bool p_force_readable_name = false);
	void remove_child(Node *p_child);

	int get_child_count(bool p_include_internal = true) const;
	Node *get_child(int p_index, bool p_include_internal = true) const;
	TypedArray<Node> get_children(bool p_include_internal = true) const;
	bool has_node(const NodePath &p_path) const;
	Node *get_node(const NodePath &p_path) const;
	Node *get_node_or_null(const NodePath &p_path) const;
	Node *find_child(const String &p_pattern, bool p_recursive = true, bool p_owned = true) const;
	TypedArray<Node> find_children(const String &p_pattern, const String &p_type = "", bool p_recursive = true, bool p_owned = true) const;
	bool has_node_and_resource(const NodePath &p_path) const;
	Node *get_node_and_resource(const NodePath &p_path, Ref<Resource> &r_res, Vector<StringName> &r_leftover_subpath, bool p_last_is_property = true) const;

	virtual void reparent(Node *p_parent, bool p_keep_global_transform = true);
	Node *get_parent() const;
	Node *find_parent(const String &p_pattern) const;

	Window *get_window() const;
	Window *get_last_exclusive_window() const;

	_FORCE_INLINE_ SceneTree *get_tree() const {
		ERR_FAIL_NULL_V(data.tree, nullptr);
		return data.tree;
	}

	_FORCE_INLINE_ bool is_inside_tree() const { return data.inside_tree; }

	bool is_ancestor_of(const Node *p_node) const;
	bool is_greater_than(const Node *p_node) const;

	NodePath get_path() const;
	NodePath get_path_to(const Node *p_node, bool p_use_unique_path = false) const;
	Node *find_common_parent_with(const Node *p_node) const;

	void add_to_group(const StringName &p_identifier, bool p_persistent = false);
	void remove_from_group(const StringName &p_identifier);
	bool is_in_group(const StringName &p_identifier) const;

	struct GroupInfo {
		StringName name;
		bool persistent = false;
	};

	void get_groups(List<GroupInfo> *p_groups) const;
	int get_persistent_group_count() const;

	void move_child(Node *p_child, int p_index);
	void _move_child(Node *p_child, int p_index, bool p_ignore_end = false);

	void set_owner(Node *p_owner);
	Node *get_owner() const;
	void get_owned_by(Node *p_by, List<Node *> *p_owned);

	void set_unique_name_in_owner(bool p_enabled);
	bool is_unique_name_in_owner() const;

	_FORCE_INLINE_ int get_index(bool p_include_internal = true) const {
		// p_include_internal = false doesn't make sense if the node is internal.
		ERR_FAIL_COND_V_MSG(!p_include_internal && data.internal_mode != INTERNAL_MODE_DISABLED, -1, "Node is internal. Can't get index with 'include_internal' being false.");
		if (!data.parent) {
			return data.index;
		}
		data.parent->_update_children_cache();

		if (!p_include_internal) {
			return data.index;
		} else {
			switch (data.internal_mode) {
				case INTERNAL_MODE_DISABLED: {
					return data.parent->data.internal_children_front_count_cache + data.index;
				} break;
				case INTERNAL_MODE_FRONT: {
					return data.index;
				} break;
				case INTERNAL_MODE_BACK: {
					return data.parent->data.internal_children_front_count_cache + data.parent->data.external_children_count_cache + data.index;
				} break;
			}
			return -1;
		}
	}

	Ref<Tween> create_tween();

	void print_tree();
	void print_tree_pretty();
	String get_tree_string();
	String get_tree_string_pretty();

	void set_scene_file_path(const String &p_scene_file_path);
	String get_scene_file_path() const;

	void set_editor_description(const String &p_editor_description);
	String get_editor_description() const;

	void set_editable_instance(Node *p_node, bool p_editable);
	bool is_editable_instance(const Node *p_node) const;
	Node *get_deepest_editable_node(Node *p_start_node) const;

#ifdef TOOLS_ENABLED
	void set_property_pinned(const String &p_property, bool p_pinned);
	bool is_property_pinned(const StringName &p_property) const;
	virtual StringName get_property_store_alias(const StringName &p_property) const;
	bool is_part_of_edited_scene() const;
#else
	bool is_part_of_edited_scene() const { return false; }
#endif