Question about multiple graph in seeker's graphMask

Hi
Seems that the seeker’s graphMask could store more than one graph for pathfinding. I am not sure how it works, say the seeker’s graphMask contains graphA and graphB. the nodes in graphA and graphB are same which means they have the same size, shape, and world position in tilemap except that the walkability and penalty are different for some nodes which are in the same world position.
so here’s the problem, how does the seeker actually search the path?

  1. if a node in graphA is walkable but non-walkable in graphB, then the node is walkable or non-walkale to the seeker?
  2. if a node in both graphA and graphB are walkable, but have different penalty, which penalty will be used for the seeker?

Hi

It works like this:

  1. The closest node to the start point is found. Only the graphs in the graph mask are searched.
  2. The closest node to the end point is found. Only the graphs in the graph mask are searched, and only nodes reachable from the start node are considered.
  3. A path is found from the start node to the end node.

If two graphs are both traversable by the agent, and they are overlapping exactly in space, the agent will probably pick a random graph just depending on floating point errors. I do not recommend this.

1 Like

Is it possible to add priority to the search for multiple graphs?
e.g. if the seeker has three graphs: graph1, graph2, graph3. the seeker will try to search graph1 first, then will try graph2 if there is no path found in graph1, and finally, it will search graph3 if no path exists for both graph1 and graph2. it is useful that sometimes I want to AIPath try to go the safest path first, if not found then I will let it find the path which contains some dangerous nodes.

That would have to be done manually, in that you’d first search for a path in graph1, then graph2, then graph3 (depending on the calculated paths).

Note that typically you’d use penalties for this. They’ll make agents try to avoid the nodes which have high penalties. See also Working with tags - A* Pathfinding Project

Hi
I can not use tags or penalties for it as they are served for other purposes and all 32 tags in the graph are all used up.

As for the solution of setting the graph mask manually, I think it would be slower and less effective than searching in one SeachPath() call: if I start SearchPath() for the graph1 at frame count 1, then at frame count 2 I get the result that the path.error is true so SearchPath() which is for graph2 is called at frame count 2 and the path result would be calculated at the frame count 3. and the more graph I have the more frame count it takes to get the path calculated in the worst case.

Hi

You can do this somewhat by querying each graph individually and using PathUtilities.IsPathPossible.

Iterate over all graphs, and use AstarPath.active.GetNearest with an NNConstrain that has its graphMask set to 1 << graphIndex. Then you can use PathUtilities.IsPathPossible to check if a path exists on that graph. You will not be able to get the exact length of the path, though (since that requires a path search).

You could also use a custom ITraversalProvider to give your agents additional penalties during the search without using tags.

1 Like

This solution is better but still has some drawbacks.
Assuming at the frame count of 5, I found that there is a path that exists for graph 2, and then I started SearchPath for it. but what if at the same frame count of 5 I submit a work item that will change the walkability of some nodes which will block the path? though I can check the next graph when I got the path.error = true (in this case the next graph is graph 3 and start a new SeachPath is IsPathPossible for graph 3 return true), it is a bit tough to write code like this. I want to keep my code as simple as possible. so if you could implement the priority search for multiple graph masks (the lower the index of the graph the higher the priority of the graph is) then I would not need to write such complex code in my project.

I am not sure if the priority search will cause performance issues or if it needs to change lots of code for it.
the agent will probably pick a random graph just depending on floating point errors
As you said it will pick a random graph, but I think it is more stable to pick a path if it is sorted by the index of the graph which would not be affected by the floating point stuff.

Hi
just think out a new solution, it is much simpler and flexible, but not sure if it works.
I need a callback before the path is calculated, by which I can change the seeker’s graph mask. in this callback, I will use the PathUtilities.IsPathPossible to check every graph in the graph mask in turn, then I will set the graph mask to the minimal index of the graph whose PathUtilities.IsPathPossible returns true.

The problem I’m not sure about is whether the graph will be updated in the duration from the callback is called to the end of the path calculated, if no update then it is acceptable, which means that I will not get a path error and research path for it because I can make sure that there is always a path exists in the last graph.