# Check if point is within Unity NavMeshSurface walkable area

I am using the NavMeshSurface component in Unity to generate a navmesh of walkable areas in a procedurally generated level. I am working on some basic behavior to use with a NavMeshAgent. I want to find a random point for the agent to wander to, but I want to check if the position is within the walkable area before telling the agent to start navigating.

The problem is that I can't find a method to check if a point is within the NavMeshSurface. My search results reference the NavMesh having a similar method but not NavMeshSurface. Is there an easy way to check if the point is in bounds? Can I access the NavMesh and ray/sphere cast against it? Any solutions would be great. If there is a different free option, I am open to exploring it.

• Can you access the NavMesh by getting NavMeshData from the NavMeshSurface and use that to test the point? Posting as a comment because I've not tried it. Sep 9, 2022 at 13:44
• Navmeshdata has no way to operate on it directly. I wonder if you could make a navmesh and add the navmeshdata from the navmeshsurface and then use the functions in navmesh to query the data. Worth an experiment. Sep 9, 2022 at 14:23

If you just want to designate a random destination for the agent to wander to, you can use NavMeshSurface.NavMeshData.sourceBounds to find a point within the bounds of the NavMeshSurface. Sure, it will contain points that aren't strictly on the path, but in most cases this shouldn't really matter -- the agent will simply wander to the nearest point that is on the path.

Here is a test script. It assumes the navmeshsurface gameobject is at origin.

It resets the agents destination every 5 seconds.

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.AI;

public class TestThing : MonoBehaviour
{
public NavMeshSurface surface;
NavMeshData data;
public NavMeshAgent agent;
public Transform target;

float timer;

Vector3 destination;

void Start()
{
data = surface.navMeshData;
agent.destination = SetRandomDest(data.sourceBounds);
Debug.Log(data.sourceBounds);
timer = 0;
}

//Update destination every 5 seconds to test
void Update()
{
timer += Time.deltaTime;
if(timer > 5)
{
agent.destination = SetRandomDest(data.sourceBounds);
Debug.Log(data.sourceBounds);
timer = 0;
}

}

Vector3 SetRandomDest(Bounds bounds)
{
var x = Random.Range(bounds.min.x, bounds.max.x);
var z = Random.Range(bounds.min.z, bounds.max.z);

destination = new Vector3(x,1, z);
target.position = destination;
return destination;
}
}

Hope that helps.