Bläddra i källkod

Improve navigation section pages

Co-authored-by: smix8 <[email protected]>
skyace65 2 år sedan
förälder
incheckning
bcb4ee80ba

BIN
tutorials/navigation/img/bake_navmesh.png


BIN
tutorials/navigation/img/baked_navmesh.png


BIN
tutorials/navigation/img/nav_2d_min_setup_step1.png


BIN
tutorials/navigation/img/nav_2d_min_setup_step2.png


BIN
tutorials/navigation/img/nav_2d_min_setup_step3.png


BIN
tutorials/navigation/img/nav_3d_min_setup_step1.png


BIN
tutorials/navigation/img/nav_3d_min_setup_step2.png


BIN
tutorials/navigation/img/nav_3d_min_setup_step3.png


BIN
tutorials/navigation/img/nav_3d_min_setup_step4.png


+ 2 - 1
tutorials/navigation/index.rst

@@ -5,4 +5,5 @@ Navigation
    :maxdepth: 1
    :name: toc-learn-features-navigation
 
-   real_time_navigation_3d
+   navigation_introduction_2d.rst
+   navigation_introduction_3d.rst

+ 147 - 0
tutorials/navigation/navigation_introduction_2d.rst

@@ -0,0 +1,147 @@
+.. _doc_navigation_overview_2d:
+
+Introduction
+===================
+
+Godot provides multiple objects, classes and servers to facilitate grid-based or mesh-based navigation
+and pathfinding for 2D and 3D games. The following section provides a quick overview over all available
+navigation related objects in Godot for 2D scenes and their primary use.
+
+2D Navigation Overview
+----------------------
+
+Godot provides the following objects and classes for 2D navigation:
+
+- :ref:`Astar2D<class_Astar2D>`
+    ``Astar2D`` objects provide an option to find the shortest path in a graph of weighted **points**.
+
+    The AStar2D class is best suited for cellbased 2D gameplay that does not require actors to reach any possible position within an area but only predefined, distinct positions.
+
+- :ref:`NavigationServer2D<class_NavigationServer2D>`
+    ``NavigationServer2D`` provides a powerful server API to find the shortest path between two positions on a area defined by a navigation mesh.
+
+    The NavigationServer is best suited for 2D realtime gameplay that does require actors to reach any possible position within an navmesh defined area.
+    Meshbased navigation scales well with large gameworlds as a large area can often be defined with a single polygon when it would require many, many grid cells.
+
+    The NavigationServer holds different navigation maps that each consist of regions that hold navigation mesh data.
+    Agents can be placed on a map for avoidance calculation.
+    RIDs are used to reference the internal maps, regions and agents when communicating with the server.
+
+    The following NavigationServer RID types are available.
+        - NavMap RID
+            Reference to a specific navigation map that holds regions and agents.
+            The map will attempt to join changed navigation meshes of regions by proximity.
+            The map will synchronise regions and agents each physics frame.
+        - NavRegion RID
+            Reference to a specific navigation region that can hold navigation mesh data.
+            The region can be enabled / disabled or the use restricted with a navigationlayer bitmask.
+        - NavAgent RID
+            Reference to a specific avoidance agent with a radius value use solely in avoidance.
+
+The following SceneTree Nodes are available as helpers to work with the NavigationServer2D API.
+
+- :ref:`NavigationRegion2D<class_NavigationRegion2D>` Node
+    A Node that holds a NavigationPolygon resource that defines a navigation mesh for the NavigationServer2D.
+    The region can be enabled / disabled.
+    The use in pathfinding can be further restricted through the navigationlayers bitmask.
+    Regions can join their navigation meshes by proximity for a combined navigation mesh.
+
+-  :ref:`NavigationAgent2D<class_NavigationAgent2D>` Node
+    An optional helper Node to facilitate common NavigationServer2D API calls for pathfinding and avoidance
+    for a Node2D inheriting parent Node.
+
+-  :ref:`NavigationObstacle2D<class_NavigationObstacle2D>` Node
+    A Node that acts as an agent with avoidance radius, to work it needs to be added under a Node2D
+    inheriting parent Node. Obstacles are intended as a last resort option for constantly moving objects
+    that cannot be re(baked) to a navigation mesh efficiently. This node also only works if RVO processing
+    is being used.
+
+The 2D navigationm eshes are defined with the following resources:
+
+- :ref:`NavigationPolygon<class_NavigationPolygon>` Resource
+    A resource that holds 2D navigation mesh data and provides polygon drawtools to define navigation areas inside the Editor as well as at runtime.
+
+    - The NavigationRegion2D Node uses this resource to define its navigation area.
+    - The NavigationServer2D uses this resource to update navmesh of individual regions.
+    - The TileSet Editor creates and uses this resource internally when defining tile navigation areas.
+
+Setup for 2D scene
+------------------
+
+The following steps show the basic setup for a minimum viable navigation in 2D that uses the
+NavigationServer2D and a NavigationAgent2D for path movement.
+
+1.) Add a NavigationRegion2D Node to the scene.
+
+2.) Click on the region node and add a new NavigationPolygon Resource to the region node
+
+.. image:: img/nav_2d_min_setup_step1.png
+
+3.) Define the moveable navigation area with the NavigationPolygon draw tool
+
+.. image:: img/nav_2d_min_setup_step2.png
+
+.. note::
+
+    The navigation mesh defines the area where an actor can stand and move with its center.
+    Leave enough margin between the navpolygon edges and collision objects to not get path following actors repeatedly stuck on collision.
+
+4.) Add a CharacterBody2D below the region node with a basic collision shape and a sprite or mesh for visuals.
+
+5.) Add a NavigationAgent2D node below the character node
+
+.. image:: img/nav_2d_min_setup_step3.png
+
+6.) Add the following script to the CharacterBody2D node. Set a movement target with the set_movement_target() function after the scene has fully loaded and the NavigationServer had time to sync.
+
+.. note::
+
+    On the first frame the NavigationServer map has not synchronised region data and any path query will return empty.
+    Use ``await get_tree().physics_frame`` to pause scripts until the NavigationServer had time to sync.
+
+.. tabs::
+ .. code-tab:: gdscript GDScript
+
+    extends CharacterBody2D
+
+    var movement_speed  : float = 200.0
+    var movement_target_position : Vector2 = Vector2(60.0,180.0)
+
+    @onready var navigation_agent : NavigationAgent2D = $NavigationAgent2D
+
+    func _ready():
+        # these values need to be adjusted for the actor's speed
+        # and the navpolygon layout as each crossed edge will create a path point
+        # If the actor moves to fast it might overshoot 
+        # multiple path points in one frame and start to backtrack
+        navigation_agent.path_desired_distance = 4.0
+        navigation_agent.target_desired_distance = 4.0
+
+        # make a deferred function call to assure the entire Scenetree is loaded
+        call_deferred("actor_setup")
+
+    func actor_setup():
+        # wait for the first physics frame so the NavigationServer can sync
+        await get_tree().physics_frame
+
+        # now that the navigation map is no longer empty set the movement target
+        set_movement_target(movement_target_position)
+
+    func set_movement_target(movement_target : Vector2):
+        navigation_agent.set_target_location(movement_target)
+
+    func _physics_process(delta):
+
+        if navigation_agent.is_target_reached():
+            return
+
+        var current_agent_position : Vector2 = global_transform.origin
+        var next_path_position : Vector2 = navigation_agent.get_next_location()
+
+        var new_velocity : Vector2 = next_path_position - current_agent_position
+        new_velocity = new_velocity.normalized()
+        new_velocity = new_velocity * movement_speed
+
+        set_velocity(new_velocity)
+
+        move_and_slide()

+ 134 - 0
tutorials/navigation/navigation_introduction_3d.rst

@@ -0,0 +1,134 @@
+.. _doc_navigation_overview_3d:
+
+Introduction
+===================
+
+Godot provides multiple objects, classes and servers to facilitate grid-based or mesh-based navigation
+and pathfinding for 2D and 3D games. The following section provides a quick overview over all available
+navigation related objects in Godot for 3D scenes and their primary use.
+
+3D Navigation Overview
+----------------------
+
+Godot provides the following objects and classes for 3D navigation:
+
+- :ref:`Astar3D<class_Astar3D>`
+    ``Astar3D`` objects provide an option to find the shortest path in a graph of weighted **points**.
+
+    The AStar3D class is best suited for cellbased 3D gameplay that does not require actors to reach any
+    possible position within an area but only predefined, distinct positions.
+
+- :ref:`NavigationServer3D<class_NavigationServer3D>`
+    ``NavigationServer3D`` provides a powerful server API to find the shortest path between two positions
+    on a area defined by a navigation mesh.
+
+    The NavigationServer is best suited for 3D realtime gameplay that does require actors to reach any
+    possible position within an navmesh defined area. Meshbased navigation scales well with large gameworlds
+    as a large area can often be defined with a single polygon when it would require many, many grid cells.
+
+    The NavigationServer holds different navigation maps that each consist of regions that hold navigation mesh
+    data. Agents can be placed on a map for avoidance calculation. RIDs are used to reference the internal maps,
+    regions and agents when communicating with the server.
+
+    The following NavigationServer RID types are available.
+        - NavMap RID
+            Reference to a specific navigation map that holds regions and agents.
+            The map will attempt to join changed navigation meshes of regions by proximity.
+            The map will synchronise regions and agents each physics frame.
+        - NavRegion RID
+            Reference to a specific navigation region that can hold navigation mesh data.
+            The region can be enabled / disabled or the use restricted with a navigationlayer bitmask.
+        - NavAgent RID
+            Reference to a specific avoidance agent with a radius value use solely in avoidance.
+
+The following SceneTree Nodes are available as helpers to work with the NavigationServer3D API.
+
+- :ref:`NavigationRegion3D<class_NavigationRegion3D>` Node
+    A Node that holds a Navigation Mesh resource that defines a navigation mesh for the NavigationServer3D.
+    The region can be enabled / disabled.
+    The use in pathfinding can be further restricted through the navigationlayers bitmask.
+    Regions can join their navigation meshes by proximity for a combined navigation mesh.
+
+-  :ref:`NavigationAgent3D<class_NavigationAgent3D>` Node
+    An optional helper Node to facilitate common NavigationServer3D API calls for pathfinding and avoidance for
+    a Node3D inheriting parent Node.
+
+-  :ref:`NavigationObstacle3D<class_NavigationObstacle3D>` Node
+    A Node that acts as an agent with avoidance radius, to work it needs to be added under a Node3D
+    inheriting parent Node. Obstacles are intended as a last resort option for constantly moving objects
+    that cannot be re(baked) to a navigation mesh efficiently. This node also only works if RVO processing
+    is being used.
+
+The 3D navigation meshes are defined with the following resources:
+
+- :ref:`NavigationMesh<class_NavigationMesh>` Resource
+    A resource that holds 3D navigation mesh data and provides 3D geometry baking options to define navigation
+    areas inside the Editor as well as at runtime.
+
+    - The NavigationRegion3D Node uses this resource to define its navigation area.
+    - The NavigationServer3D uses this resource to update navmesh of individual regions.
+    - The GridMap Editor uses this resource when specific navigation meshes are defined for each gridcell.
+
+Setup for 3D scene
+------------------
+
+The following steps show how to setup a minimum viable navigation in 3D that uses the NavigationServer3D and
+a NavigationAgent3D for path movement.
+
+1.) Add a NavigationRegion3D Node to the scene.
+
+2.) Click on the region node and add a new :ref:`NavigationMesh<class_NavigationMesh>` Resource to the region node
+
+.. image:: img/nav_3d_min_setup_step1.png
+
+3.) Add a new MeshInstance node as a child of the region node
+
+4.) Select the meshinstance node and add a new PlaneMesh and increase the xy size to 10.
+
+5.) Select the region node again and press the "Bake Navmesh" button on the top bar
+
+.. image:: img/nav_3d_min_setup_step2.png
+
+7.) Now a transparent navigation mesh appeared that hovers some distance on top the planemesh.
+
+.. image:: img/nav_3d_min_setup_step3.png
+
+8.) Add a CharacterBody3D below the region node with a basic collision shape and some mesh for visuals.
+
+9.) Add a NavigationAgent3D node below the character node
+
+.. image:: img/nav_3d_min_setup_step4.png
+
+10.) Add a script to the CharacterBody3D node with the following content.
+
+.. tabs::
+ .. code-tab:: gdscript GDScript
+
+    extends CharacterBody3D
+
+    var movement_speed  : float = 4.0
+
+    @onready var navigation_agent = $NavigationAgent3D
+
+    func set_movement_target(movement_target : Vector3):
+        navigation_agent.set_target_location(movement_target)
+
+    func _physics_process(delta):
+
+        var current_agent_position : Vector3 = global_transform.origin
+        var next_path_position : Vector3 = navigation_agent.get_next_location()
+
+        var new_velocity : Vector3 = next_path_position - current_agent_position
+        new_velocity = new_velocity.normalized()
+        new_velocity = new_velocity * movement_speed
+
+        set_velocity(new_velocity)
+        move_and_slide()
+
+Set a movement target with the set_movement_target() function after the scene has fully loaded.
+Also add a Camera3D and some light and environment to see something.
+
+.. warning::
+
+    On the first frame the NavigationServer map has not synchronised region data and any path query will return empty.
+    Use ``await get_tree().physics_frame`` to pause scripts until the NavigationServer had time to sync.

+ 0 - 92
tutorials/navigation/real_time_navigation_3d.rst

@@ -1,92 +0,0 @@
-.. _doc_real_time_navigation_3d:
-
-Real Time Navigation (3D)
-=========================
-
-Introduction
-------------
-
-Pathfinding in a 3D environment is crucial for many games, it's commonly
-how non directly controlled characters or entities find their way around
-an environment. Godot provides several nodes for this purpose:
-
--  :ref:`NavigationRegion3D<class_NavigationRegion3D>`
--  :ref:`NavigationAgent3D<class_NavigationAgent3D>`
--  :ref:`NavigationObstacle3D<class_NavigationObstacle3D>`
-
-The map and navigation regions
-------------------------------
-
-The "map" is the entire world for navigation, it's similar to "space" for
-the physics engine. It's comprised of navigation regions, these regions
-define what parts of the world that can be navigated around by navigation
-agents.
-
-To create a navigation region add the `NavigationRegion3D<class_NavigationRegion3D>`
-node to a 3D scene. Next in the inspector for that region create or add a
-:ref:`NavigationMesh<class_NavigationMesh>`. The navmesh contains options
-for how it will be generated when it's baked. The geometry options control
-which nodes, and types of nodes, are used to bake the mesh. A full
-description of each setting and how it works can be found in the :ref:`NavigationMesh class reference<class_NavigationMesh>`.
-
-Once the settings have been properly configured press the "Bake NavMesh"
-button at the top of the inspector to generate it.
-
-.. image:: img/bake_navmesh.png
-
-.. note::
-
-    It can also be generated at runtime using the `bake_navigation_region()`
-    method of the navigation region node.
-
-Once the mesh has finished generating you should see the transparent
-navigation mesh above the areas in the scene that can be navigated to.
-
-.. image:: img/baked_navmesh.png
-
-Keep in mind that the navmesh shows where the center of an entity can
-go. For example, if you set the agent radius to 0.5 then the
-navigation mesh will have a distance of 0.5 from any ledges or walls
-to prevent clipping into the wall or hanging off of the edge.
-
-Navigation agents can moved from one region to another if they are next
-to each other. Additionally A baked navmesh can be moved at runtime and
-agents will still be able to navigate onto it from another region.
-For example, navigating onto a moving platform that has stopped will work.
-
-NavigationAgent3D
------------------
-
-Navigation agent nodes are what actually does the pathfinding in a scene,
-one can be attached to the root node of an entity that needs to navigate.
-
-To have it pathfind use its `set_target_location` method. Once the target
-has been set a path will be generated to the node using navigation regions,
-with several points on the way to the final destination.
-
-RVO processing
---------------
-
-RVO stands for reciprocal velocity obstacle. RVO processing is a way to
-pathfind while taking into account other agents and physics bodies that
-are also moving.
-
-To use it set a target like normal. Then an agent needs to fetch its next
-nav path location, and compute its velocity to that location. Instead
-of using that value to move use it to set the velocity on the agent
-with `set_velocity`. Then a new velocity that takes into account other
-agents and obstacles is generated and emitted with the signal `velocity_computed`.
-
-However agents can only take into account a set number of other nearby
-agents, this is the :ref:`max neighbors<class_NavigationAgent3D_property_max_neighbors>`
-property of an agent and can be adjusted. This is **not** a limit for
-how many agents can use a navigation region at the same time.
-
-NavigationObstacle3D
---------------------
-
-This node is used to mark physics bodies that move around a navigation area
-that agents need to avoid (this will only work if you use RVO processing).
-For example, this node would be useful for pieces of debris in a destructible
-environment. Add it as the child of a physics body and navigation agent
-nodes will avoid it while pathfinding.