Beispiel #1
0
        /// <summary>
        /// Creates a new tile set.
        /// </summary>
        /// <remarks>
        /// <para>
        /// The bounds is normally based on the desired origin of the navigation mesh
        /// and the maximum bounds of the input geometry.
        /// </para>
        /// </remarks>
        /// <param name="boundsMin">The minimum AABB bounds of the set.</param>
        /// <param name="boundsMax">The maximum AABB counds of the set.</param>
        /// <param name="config">The shared NMGen configuration.</param>
        /// <param name="geom">The input geometry.</param>
        /// <returns>A new tile set, or null on error.</returns>
        public static TileSetDefinition Create(Vector3 boundsMin, Vector3 boundsMax
                                               , NMGenParams config
                                               , InputGeometry geom)
        {
            if (config == null || !config.IsValid() ||
                !TriangleMesh.IsBoundsValid(boundsMin, boundsMax) ||
                geom == null ||
                config.tileSize <= 0)
            {
                return(null);
            }

            int w;
            int d;

            NMGen.DeriveSizeOfTileGrid(boundsMin, boundsMax
                                       , config.XZCellSize
                                       , config.tileSize
                                       , out w, out d);

            if (w < 1 || d < 1)
            {
                return(null);
            }

            return(new TileSetDefinition(w, d, boundsMin, boundsMax, config, geom));
        }
Beispiel #2
0
    internal bool InitializeBuild(BuildContext context, bool fromTarget)
    {
        Navmesh navmesh = null;

        if (fromTarget)
        {
            if (!CanLoadFromTarget(context, true))
            {
                return(false);
            }

            navmesh = BuildTarget.GetNavmesh();

            SetConfigFromTargetIntern(navmesh);
        }

        mIsDirty = true;

        // Note: If loading from the target, the tile size was already validated.
        // So it won't trigger this adjustment.
        if (mConfig.TileSize != 0 &&
            mConfig.TileSize < MinAllowedTileSize)
        {
            string msg = string.Format("Tile size too small. Reverting tile size from"
                                       + " {0} to 0 (non-tiled). Minimum tile size is {1}"
                                       , mConfig.TileSize, MinAllowedTileSize);

            context.LogWarning(msg, this);

            mConfig.TileSize = 0;
        }

        if (mConfig.TileSize == 0)
        {
            mBuildData.Resize(1, 1);
        }
        else
        {
            // Need to check to see if the the build is truly tiled.

            int w;
            int d = 0;

            if (navmesh == null)
            {
                NMGen.DeriveSizeOfTileGrid(mBoundsMin, mBoundsMax
                                           , mConfig.XZCellSize, mConfig.TileSize
                                           , out w, out d);
            }
            else
            {
                // Existing navmesh will always be tiled.
                w = 2;
            }

            if (w > 1 || d > 1)
            {
                mTileSet = TileSetDefinition.Create(mBoundsMin, mBoundsMax
                                                    , mConfig.GetConfig()
                                                    , mInputGeom);

                if (mTileSet == null)
                {
                    context.LogError("Create tile build definition: Unexpected error."
                                     + " Invalid input data or configuration."
                                     , this);

                    return(false);
                }

                mBuildData.Resize(mTileSet.Width, mTileSet.Depth);
            }
            else
            {
                // Not really tiled.
                mBuildData.Resize(1, 1);
            }
        }

        if (navmesh != null)
        {
            // Need to load the tiles from existing navmesh.

            NavmeshTileExtract[] tiles;
            NavmeshParams        meshConfig;

            NavStatus status = Navmesh.ExtractTileData(navmesh.GetSerializedMesh()
                                                       , out tiles
                                                       , out meshConfig);

            if ((status & NavStatus.Failure) != 0)
            {
                context.LogError("Could not extract the tile data from the target's"
                                 + " navigation mesh. (Can't initialize from build target.)"
                                 , this);
                return(false);
            }

            foreach (NavmeshTileExtract tile in tiles)
            {
                int polyCount = tile.header.polyCount;

                if (polyCount == 0)
                {
                    continue;
                }

                int tx = tile.header.tileX;
                int tz = tile.header.tileZ;

                if (tx >= mBuildData.Width || tz >= mBuildData.Depth)
                {
                    // Shouldn't happen.  Probably indicates in internal error
                    // of some type.

                    string msg = string.Format("The existing navigation mesh"
                                               + " contains a tile outside the expected range. Ignoring"
                                               + " the tile. (Tile: [{0},{1}])"
                                               , tx, tz);

                    context.LogWarning(msg, this);

                    continue;
                }

                mBuildData.SetAsBaked(tx, tz, tile.data, polyCount);
            }
        }

        // Note: Dirty state was set earlier in the code.

        return(true);
    }