public FormationQuerySystem(Formation formation)
        {
            FormationQuerySystem formationQuerySystem = this;

            this.Formation = formation;
            Mission mission = Mission.Current;

            this._formationPower = new QueryData <float>(new Func <float>(formation.GetFormationPower), 2.5f);
            this._formationMeleeFightingPower = new QueryData <float>(new Func <float>(formation.GetFormationMeleeFightingPower), 2.5f);
            this._averagePosition             = new QueryData <Vec2>((Func <Vec2>)(() =>
            {
                Vec2 vec2  = formation.CountOfUnitsWithoutDetachedOnes > 1 ? formation.GetAveragePositionOfUnits(true, true) : (formation.CountOfUnitsWithoutDetachedOnes > 0 ? formation.GetAveragePositionOfUnits(true, false) : formation.OrderPosition.AsVec2);
                float time = MBCommon.GetTime(MBCommon.TimeType.Mission);
                float num  = time - formationQuerySystem._lastAveragePositionCalculateTime;
                if ((double)num > 0.0)
                {
                    formationQuerySystem._currentVelocity.SetValue((vec2 - formationQuerySystem._averagePosition.GetCachedValue()) * (1f / num), time);
                }
                formationQuerySystem._lastAveragePositionCalculateTime = time;
                return(vec2);
            }), 0.05f);
            this._currentVelocity = new QueryData <Vec2>((Func <Vec2>)(() =>
            {
                formationQuerySystem._averagePosition.Evaluate(MBCommon.GetTime(MBCommon.TimeType.Mission));
                return(formationQuerySystem._currentVelocity.GetCachedValue());
            }), 1f);
            this._estimatedDirection = new QueryData <Vec2>((Func <Vec2>)(() =>
            {
                if (formation.CountOfUnitsWithoutDetachedOnes > 0)
                {
                    Vec2 averagePositionOfUnits = formation.GetAveragePositionOfUnits(true, false);
                    float num1 = 0.0f;
                    float num2 = 0.0f;
                    Vec2 localAveragePosition = formation.OrderLocalAveragePosition;
                    foreach (Agent looseDetachedOne in formation.UnitsWithoutLooseDetachedOnes)
                    {
                        Vec2?positionOfUnitOrDefault = formation.arrangement.GetLocalPositionOfUnitOrDefault((IFormationUnit)looseDetachedOne);
                        if (positionOfUnitOrDefault.HasValue)
                        {
                            Vec2 vec2   = positionOfUnitOrDefault.Value;
                            Vec2 asVec2 = looseDetachedOne.Position.AsVec2;
                            num1       += (float)(((double)vec2.x - (double)localAveragePosition.x) * ((double)asVec2.x - (double)averagePositionOfUnits.x) + ((double)vec2.y - (double)localAveragePosition.y) * ((double)asVec2.y - (double)averagePositionOfUnits.y));
                            num2       += (float)(((double)vec2.x - (double)localAveragePosition.x) * ((double)asVec2.y - (double)averagePositionOfUnits.y) - ((double)vec2.y - (double)localAveragePosition.y) * ((double)asVec2.x - (double)averagePositionOfUnits.x));
                        }
                    }
                    float num3 = 1f / (float)formation.CountOfUnitsWithoutDetachedOnes;
                    float num4 = num1 * num3;
                    float num5 = num2 * num3;
                    float num6 = MathF.Sqrt((float)((double)num4 * (double)num4 + (double)num5 * (double)num5));
                    if ((double)num6 > 0.0)
                    {
                        double num7 = Math.Acos((double)MBMath.ClampFloat(num4 / num6, -1f, 1f));
                        Vec2 vec2_1 = Vec2.FromRotation((float)num7);
                        Vec2 vec2_2 = Vec2.FromRotation((float)-num7);
                        float num8  = 0.0f;
                        float num9  = 0.0f;
                        foreach (Agent looseDetachedOne in formation.UnitsWithoutLooseDetachedOnes)
                        {
                            Vec2?positionOfUnitOrDefault = formation.arrangement.GetLocalPositionOfUnitOrDefault((IFormationUnit)looseDetachedOne);
                            if (positionOfUnitOrDefault.HasValue)
                            {
                                Vec2 parentUnitF1 = vec2_1.TransformToParentUnitF(positionOfUnitOrDefault.Value - localAveragePosition);
                                Vec2 parentUnitF2 = vec2_2.TransformToParentUnitF(positionOfUnitOrDefault.Value - localAveragePosition);
                                Vec2 asVec2       = looseDetachedOne.Position.AsVec2;
                                num8 += (parentUnitF1 - asVec2 + averagePositionOfUnits).LengthSquared;
                                num9 += (parentUnitF2 - asVec2 + averagePositionOfUnits).LengthSquared;
                            }
                        }
                        return((double)num8 >= (double)num9 ? vec2_2 : vec2_1);
                    }
                }
                return(new Vec2(0.0f, 1f));
            }), 0.2f);
            this._medianPosition = new QueryData <WorldPosition>((Func <WorldPosition>)(() =>
            {
                if (formation.CountOfUnitsWithoutDetachedOnes != 0)
                {
                    return(formation.CountOfUnitsWithoutDetachedOnes != 1 ? formation.GetMedianAgent(true, true, formationQuerySystem.AveragePosition).GetWorldPosition() : formation.GetMedianAgent(true, false, formationQuerySystem.AveragePosition).GetWorldPosition());
                }
                if (formation.CountOfUnits == 0)
                {
                    return(formation.OrderPosition);
                }
                return(formation.CountOfUnits != 1 ? formation.GetMedianAgent(false, true, formationQuerySystem.AveragePosition).GetWorldPosition() : formation.GetFirstUnit().GetWorldPosition());
            }), 0.05f);
            this._averageAllyPosition = new QueryData <Vec2>((Func <Vec2>)(() =>
            {
                IEnumerable <Formation> source = mission.Teams.GetAlliesOf(formation.Team, true).SelectMany <TaleWorlds.MountAndBlade.Team, Formation>((Func <TaleWorlds.MountAndBlade.Team, IEnumerable <Formation> >)(t => t.FormationsIncludingSpecial)).Where <Formation>(closure_1 ?? (closure_1 = (Func <Formation, bool>)(f => f != formation)));
                if (source.IsEmpty <Formation>())
                {
                    return(closure_0.AveragePosition);
                }
                Vec2 zero = Vec2.Zero;
                int num   = 0;
                foreach (Formation formation1 in source)
                {
                    zero += formation1.GetAveragePositionOfUnits(false, false) * (float)formation1.CountOfUnits;
                    num  += formation1.CountOfUnits;
                }
                return(num == 0 ? Vec2.Invalid : zero *(1f / (float)num));
            }), 5f);
            this._idealAverageDisplacement = new QueryData <float>((Func <float>)(() => (float)Math.Sqrt(Math.Pow((double)formation.Width / 2.0, 2.0) + Math.Pow((double)formation.Depth / 2.0, 2.0)) / 2f), 5f);
            this._formationIntegrityData   = new QueryData <FormationQuerySystem.FormationIntegrityDataGroup>((Func <FormationQuerySystem.FormationIntegrityDataGroup>)(() =>
            {
                if (formation.CountOfUnitsWithoutDetachedOnes > 0)
                {
                    float num1 = 0.0f;
                    List <IFormationUnit> allUnits = formation.arrangement.GetAllUnits();
                    Vec3 vec3;
                    for (int index = 0; index < allUnits.Count; ++index)
                    {
                        Agent unit  = allUnits[index] as Agent;
                        double num2 = (double)num1;
                        Vec2 globalPositionOfUnit = formation.GetCurrentGlobalPositionOfUnit(unit, false);
                        vec3                 = unit.Position;
                        Vec2 asVec2          = vec3.AsVec2;
                        double lengthSquared = (double)(globalPositionOfUnit - asVec2).LengthSquared;
                        num1                 = (float)(num2 + lengthSquared);
                    }
                    Vec2 vec2_1;
                    for (int index = 0; index < formation.LooseDetachedUnits.Count; ++index)
                    {
                        Agent looseDetachedUnit   = formation.LooseDetachedUnits[index];
                        double num2               = (double)num1;
                        Vec2 globalPositionOfUnit = formation.GetCurrentGlobalPositionOfUnit(looseDetachedUnit, false);
                        vec3                 = looseDetachedUnit.Position;
                        Vec2 asVec2          = vec3.AsVec2;
                        vec2_1               = globalPositionOfUnit - asVec2;
                        double lengthSquared = (double)vec2_1.LengthSquared;
                        num1                 = (float)(num2 + lengthSquared);
                    }
                    float num3  = (float)((double)num1 / (double)formation.CountOfUnitsWithoutDetachedOnes * 4.0);
                    float num4  = 0.0f;
                    Vec2 vec2_2 = Vec2.Zero;
                    float num5  = 0.0f;
                    int num6    = 0;
                    for (int index = 0; index < allUnits.Count; ++index)
                    {
                        Agent unit = allUnits[index] as Agent;
                        Vec2 globalPositionOfUnit = formation.GetCurrentGlobalPositionOfUnit(unit, false);
                        vec3                = unit.Position;
                        Vec2 asVec2_1       = vec3.AsVec2;
                        vec2_1              = globalPositionOfUnit - asVec2_1;
                        float lengthSquared = vec2_1.LengthSquared;
                        if ((double)lengthSquared < (double)num3)
                        {
                            num4         += lengthSquared;
                            Vec2 vec2_3   = vec2_2;
                            vec3          = unit.AverageVelocity;
                            Vec2 asVec2_2 = vec3.AsVec2;
                            vec2_2        = vec2_3 + asVec2_2;
                            num5         += unit.MaximumForwardUnlimitedSpeed;
                            ++num6;
                        }
                    }
                    for (int index = 0; index < formation.LooseDetachedUnits.Count; ++index)
                    {
                        Agent looseDetachedUnit   = formation.LooseDetachedUnits[index];
                        Vec2 globalPositionOfUnit = formation.GetCurrentGlobalPositionOfUnit(looseDetachedUnit, false);
                        vec3                = looseDetachedUnit.Position;
                        Vec2 asVec2_1       = vec3.AsVec2;
                        vec2_1              = globalPositionOfUnit - asVec2_1;
                        float lengthSquared = vec2_1.LengthSquared;
                        if ((double)lengthSquared < (double)num3)
                        {
                            num4         += lengthSquared;
                            Vec2 vec2_3   = vec2_2;
                            vec3          = looseDetachedUnit.AverageVelocity;
                            Vec2 asVec2_2 = vec3.AsVec2;
                            vec2_2        = vec2_3 + asVec2_2;
                            num5         += looseDetachedUnit.MaximumForwardUnlimitedSpeed;
                            ++num6;
                        }
                    }
                    if (num6 > 0)
                    {
                        Vec2 vec2_3 = vec2_2 * (1f / (float)num6);
                        float x     = num4 / (float)num6;
                        float num2  = num5 / (float)num6;
                        FormationQuerySystem.FormationIntegrityDataGroup integrityDataGroup;
                        integrityDataGroup.AverageVelocityExcludeFarAgents          = vec2_3;
                        integrityDataGroup.DeviationOfPositionsExcludeFarAgents     = MathF.Sqrt(x);
                        integrityDataGroup.AverageMaxUnlimitedSpeedExcludeFarAgents = num2;
                        return(integrityDataGroup);
                    }
                }
                FormationQuerySystem.FormationIntegrityDataGroup integrityDataGroup1;
                integrityDataGroup1.AverageVelocityExcludeFarAgents          = Vec2.Zero;
                integrityDataGroup1.DeviationOfPositionsExcludeFarAgents     = 0.0f;
                integrityDataGroup1.AverageMaxUnlimitedSpeedExcludeFarAgents = 0.0f;
                return(integrityDataGroup1);
            }), 1f);
            this._formationDispersedness = new QueryData <float>((Func <float>)(() =>
            {
                if (formation.CountOfUnits == 0)
                {
                    return(0.0f);
                }
                float num1 = 0.0f;
                int num2   = 0;
                foreach (IFormationUnit allUnit in formation.arrangement.GetAllUnits())
                {
                    Vec2?positionOfUnitOrDefault = formation.arrangement.GetLocalPositionOfUnitOrDefault(allUnit);
                    if (positionOfUnitOrDefault.HasValue)
                    {
                        MatrixFrame m = new MatrixFrame(Mat3.Identity, new Vec3(positionOfUnitOrDefault.Value));
                        MatrixFrame matrixFrame;
                        ref MatrixFrame local = ref matrixFrame;
                        Mat3 rot = new Mat3(new Vec3(formation.Direction.RightVec()), new Vec3(formation.Direction), new Vec3(z: 1f));
                        WorldPosition worldPosition = formation.QuerySystem.MedianPosition;
                        Vec3 navMeshVec3            = worldPosition.GetNavMeshVec3();
                        local = new MatrixFrame(rot, navMeshVec3);
                        MatrixFrame parent = matrixFrame.TransformToParent(m);
                        double num3        = (double)num1;
                        worldPosition      = (allUnit as Agent).GetWorldPosition();
                        double num4        = (double)worldPosition.GetGroundVec3().Distance(parent.origin);
                        num1 = (float)(num3 + num4);
                    }