private void RefreshLineOfSight(ILineOfSightEntity lineOfSightEntity, int needRefreshBits)
    {
        if (!lineOfSightEntity.LineOfSightActive)
        {
            return;
        }
        MajorEmpire majorEmpire = lineOfSightEntity.Empire as MajorEmpire;

        if (majorEmpire == null)
        {
            return;
        }
        short num = (short)(majorEmpire.Bits | lineOfSightEntity.EmpireInfiltrationBits);

        if ((needRefreshBits & (int)num) == 0)
        {
            return;
        }
        lineOfSightEntity.LineOfSightDirty = false;
        if (!lineOfSightEntity.WorldPosition.IsValid)
        {
            return;
        }
        WorldParameters worldParameters         = this.world.WorldParameters;
        int             lineOfSightVisionRange  = lineOfSightEntity.LineOfSightVisionRange;
        int             lineOfSightVisionHeight = lineOfSightEntity.LineOfSightVisionHeight;
        int             num2 = 0;

        if (lineOfSightEntity.LineOfSightData == null)
        {
            lineOfSightEntity.LineOfSightData = new LineOfSightData();
        }
        LineOfSightData lineOfSightData = lineOfSightEntity.LineOfSightData;

        if (lineOfSightVisionRange < 0)
        {
            return;
        }
        short num3 = (short)lineOfSightVisionRange;

        if (this.tempRect == null)
        {
            this.tempRect = new WorldRect(lineOfSightEntity.WorldPosition, WorldOrientation.East, num3, num3, num3, num3, worldParameters);
        }
        else
        {
            this.tempRect.Update(lineOfSightEntity.WorldPosition, WorldOrientation.East, num3, num3, num3, num3, worldParameters);
        }
        this.rectVirtualPositions.Clear();
        this.tempRect.FillVirtualWorldPositions(ref this.rectVirtualPositions);
        VisibilityController.Position position = new VisibilityController.Position(WorldPosition.Invalid, WorldPosition.Invalid, -1);
        for (int i = 0; i < this.rectVirtualPositions.Count; i++)
        {
            if (lineOfSightEntity.WorldPosition == WorldPosition.GetValidPosition(this.rectVirtualPositions[i], worldParameters))
            {
                position = new VisibilityController.Position(this.rectVirtualPositions[i], lineOfSightEntity.WorldPosition, 0);
                break;
            }
        }
        Diagnostics.Assert(position.ValidWorldPosition.IsValid);
        this.potentialPositions.Clear();
        for (int j = 0; j < this.rectVirtualPositions.Count; j++)
        {
            WorldPosition worldPosition = this.rectVirtualPositions[j];
            WorldPosition validPosition = WorldPosition.GetValidPosition(worldPosition, worldParameters);
            if (validPosition.IsValid)
            {
                int distance = WorldPosition.GetDistance(position.ValidWorldPosition, validPosition, worldParameters.IsCyclicWorld, worldParameters.Columns);
                if (distance <= lineOfSightVisionRange)
                {
                    this.potentialPositions.Add(new VisibilityController.Position(worldPosition, validPosition, distance));
                }
            }
        }
        this.potentialPositions.Sort((VisibilityController.Position position1, VisibilityController.Position position2) => position1.Distance.CompareTo(position2.Distance));
        lineOfSightData.Arcs.Clear();
        float radius = ((float)lineOfSightVisionRange + 0.1f) * 2f * Hexagon.One.Radius;

        lineOfSightData.Arcs.AddFirst(new Arc(position.GeometryPosition, 0f, 6.28308535f, radius));
        bool flag = this.EnableDetection;

        if (flag)
        {
            num2  = lineOfSightEntity.LineOfSightDetectionRange;
            flag &= (num2 > 0);
        }
        for (int k = 0; k < this.potentialPositions.Count; k++)
        {
            VisibilityController.Position obstaclePosition = this.potentialPositions[k];
            bool flag2 = obstaclePosition.Distance > lineOfSightVisionRange || this.IsWorldPositionObstructingVision(position.ValidWorldPosition, obstaclePosition.ValidWorldPosition, lineOfSightVisionHeight, lineOfSightEntity.IgnoreFog);
            if (flag && obstaclePosition.Distance > num2)
            {
                flag = false;
            }
            LinkedListNode <Arc> linkedListNode = lineOfSightData.Arcs.First;
            while (linkedListNode != null)
            {
                Arc value = linkedListNode.Value;
                linkedListNode = linkedListNode.Next;
                if (flag2)
                {
                    if (Helper.IsHexagonIntersectArc(value, obstaclePosition.GeometryPosition))
                    {
                        this.SplitArc(lineOfSightData, value, obstaclePosition);
                        this.SetWorldPositionAsExplored(obstaclePosition.ValidWorldPosition, majorEmpire, num);
                    }
                }
                else if (value.Contains(obstaclePosition.GeometryPosition))
                {
                    if (flag)
                    {
                        this.SetWorldPositionAsDetected(obstaclePosition.ValidWorldPosition, majorEmpire, num, lineOfSightEntity.VisibilityAccessibilityLevel);
                        break;
                    }
                    this.SetWorldPositionAsVisible(obstaclePosition.ValidWorldPosition, majorEmpire, num, lineOfSightEntity.VisibilityAccessibilityLevel);
                    break;
                }
            }
        }
    }