Friday, November 26, 2010

Detour Return Codes Take 2

I just update the Detour status labels based on recent feedback. The code is in in R255. The return value is now bitfield instead of a single enum. This to pass both error messages as well as few bits of information about the quality of the result.

The high level statuses are DT_FAILURE, DT_SUCCESS, and DT_IN_PROGRESS. The rest of the bits are used to describe mode detail about the status. To test if a status is one of the above, you should use the helper functions dtStatusSucceed(), dtStatusFailed() or dtStatusInProgress().

dtStatus status = m_navQuery->init(m_navMesh, 2048);
if (dtStatusFailed(status))
return false;
In many cases of success and failure, you can get one or more bits of extra information why things failed or if the quality of result is degraded. The detail flags are:
  • DT_WRONG_MAGIC: the input data you passed had wrong magic number. In practice this means that you are trying deed bad data to Detour. Failure.
  • DT_WRONG_VERSION: the input data is in different version than Detour expects. Failure.
  • DT_OUT_OF_MEMORY: the operation could not allocate enough memory. Currently this applies to init methods. Failure.
  • DT_INVALID_PARAM: one or more of the input parameters had invalid values. Usually this means that you passed a poly ref which is not valid. Failure.
  • DT_BUFFER_TOO_SMALL: the buffer to store the result was too small. Success.
  • DT_OUT_OF_NODES: query ran our of nodes during search. If this happens often, you should increase maxNodes. Success.
  • DT_PARTIAL_RESULT: query did not reach the end location, returning best guess. Success.
In case a function call fails, it usually returns only one flag. If a function call succeeds, it may return multiple flags indicating the result quality. The flag DT_BUFFER_TOO_SMALL is also use store/restore tile state and in that case it is returned to describe why the function call failed.

Some more examples:
dtStatus status = m_navQuery->init(m_navMesh, 2048);
if (dtStatusFailed(status))
if (dtStatusDetail(status, DT_OUT_OF_MEMORY))
printf("Out of memory initializing navmesh query.\n");
return false;

dtStatus status = m_navQuery->findPath(sref, eref, spos, epos, filter, polys, &npolys, MAX_POLYS);
if (dtStatusSucceed(status))
if (dtStatusDetail(status, DT_BUFFER_TOO_SMALL))
// The path result is longer than MAX_POLYS.
if (dtStatusDetail(status, DT_PARTIAL_RESULT))
// Could not reach end location, the path leads to a location near the end point.

No comments:

Post a Comment