コード例 #1
0
        public void RecalculateFromPosition(Point viewerPosition)
        {
            // Test from each corner of source square to center of target square
            PointF[] cornersToTest = { new PointF(viewerPosition.X,     viewerPosition.Y),
                                       new PointF(viewerPosition.X + 1, viewerPosition.Y),
                                       new PointF(viewerPosition.X,     viewerPosition.Y + 1),
                                       new PointF(viewerPosition.X + 1, viewerPosition.Y + 1) };

            this.VisibilityMap = null;
            foreach (var point in cornersToTest)
            {
                VisibilityMap cornerMap = this.GenerateVisibilityMapForPosition(point);
                if (this.VisibilityMap == null)
                {
                    this.VisibilityMap = cornerMap;
                }
                else
                {
                    for (int x = 0; x < cornerMap.Width; ++x)
                    {
                        for (int y = 0; y < cornerMap.Height; ++y)
                        {
                            this.VisibilityMap[x, y] = (OcclusionLevel)Math.Min((int)this.VisibilityMap[x, y], (int)cornerMap[x, y]);
                        }
                    }
                }
            }

            // Calculate cover spots
            for (int x = 0; x < this.VisibilityMap.Width; ++x)
            {
                for (int y = 0; y < this.VisibilityMap.Height; ++y)
                {
                    if (this.VisibilityMap[x, y] == OcclusionLevel.Obscured)
                    {
                        if (TestSquare(x, y - 1) == OcclusionLevel.Visible ||
                            TestSquare(x, y + 1) == OcclusionLevel.Visible ||
                            TestSquare(x - 1, y) == OcclusionLevel.Visible ||
                            TestSquare(x + 1, y) == OcclusionLevel.Visible)
                        {
                            this.VisibilityMap[x, y] = OcclusionLevel.Cover;
                        }
                    }
                }
            }

            //PointF centerOfSquare = new PointF((float)viewerPosition.X + 0.5f, (float)viewerPosition.Y + 0.5f);
            //this.VisibilityMap = this.GenerateVisibilityMapForPosition(centerOfSquare);
            //this.TestCorners(viewerPosition);
        }
コード例 #2
0
        private void TestCorners(Point viewerPosition)
        {
            List <PointF> cornersToTest = new List <PointF>();

            if (this.VisibilityMap[viewerPosition.X - 1, viewerPosition.Y - 1] != OcclusionLevel.Obscured &&
                (this.VisibilityMap[viewerPosition.X, viewerPosition.Y - 1] == OcclusionLevel.Obscured ||
                 this.VisibilityMap[viewerPosition.X - 1, viewerPosition.Y] == OcclusionLevel.Obscured))
            {
                // test upper left corner, wall either above or left
                cornersToTest.Add(new PointF((float)viewerPosition.X, (float)viewerPosition.Y));
            }

            if (this.VisibilityMap[viewerPosition.X + 1, viewerPosition.Y - 1] != OcclusionLevel.Obscured &&
                (this.VisibilityMap[viewerPosition.X, viewerPosition.Y - 1] == OcclusionLevel.Obscured ||
                 this.VisibilityMap[viewerPosition.X + 1, viewerPosition.Y] == OcclusionLevel.Obscured))
            {
                // test upper right corner, wall either above or right
                cornersToTest.Add(new PointF((float)viewerPosition.X + 1, (float)viewerPosition.Y));
            }

            if (this.VisibilityMap[viewerPosition.X - 1, viewerPosition.Y + 1] != OcclusionLevel.Obscured &&
                (this.VisibilityMap[viewerPosition.X, viewerPosition.Y + 1] == OcclusionLevel.Obscured ||
                 this.VisibilityMap[viewerPosition.X - 1, viewerPosition.Y] == OcclusionLevel.Obscured))
            {
                // test lower-left corner, wall either left or bottom
                cornersToTest.Add(new PointF((float)viewerPosition.X, (float)viewerPosition.Y + 1));
            }

            if (this.VisibilityMap[viewerPosition.X + 1, viewerPosition.Y + 1] != OcclusionLevel.Obscured &&
                (this.VisibilityMap[viewerPosition.X, viewerPosition.Y + 1] == OcclusionLevel.Obscured ||
                 this.VisibilityMap[viewerPosition.X + 1, viewerPosition.Y] == OcclusionLevel.Obscured))
            {
                // test lower-right corner, wall either right or bottom
                cornersToTest.Add(new PointF((float)viewerPosition.X + 1, (float)viewerPosition.Y + 1));
            }

            // if we have corners to test, then run through the whole visibility map from that corner and union it to our result
            foreach (var point in cornersToTest)
            {
                VisibilityMap cornerMap = this.GenerateVisibilityMapForPosition(point);
                for (int x = 0; x < cornerMap.Width; ++x)
                {
                    for (int y = 0; y < cornerMap.Height; ++y)
                    {
                        this.VisibilityMap[x, y] = this.VisibilityMap[x, y] == OcclusionLevel.Obscured ? OcclusionLevel.Obscured : cornerMap[x, y];
                    }
                }
            }
        }
コード例 #3
0
        private VisibilityMap GenerateVisibilityMapForPosition(PointF viewerLocation)
        {
            VisibilityMap visData = new VisibilityMap(this.Max.X - this.Min.X, this.Max.Y - this.Min.Y);

            for (int x = this.Min.X; x < this.Max.X; ++x)
            {
                for (int y = this.Min.Y; y < this.Max.Y; ++y)
                {
                    PointF targetLocation = new PointF((float)x + 0.5f, (float)y + 0.5f);
                    visData[x - this.Min.X, y - this.Min.Y] = this.GetOcclusion(viewerLocation, targetLocation);
                }
            }

            return(visData);
        }