Example #1
0
        public SnookerMatchScore Clone()
        {
            SnookerMatchScore obj = new SnookerMatchScore();

            obj.ID                   = this.ID;
            obj.YourAthleteID        = this.YourAthleteID;
            obj.YourName             = this.YourName;
            obj.YourPicture          = this.YourPicture;
            obj.OpponentAthleteID    = this.OpponentAthleteID;
            obj.OpponentName         = this.OpponentName;
            obj.OpponentPicture      = this.OpponentPicture;
            obj.OpponentConfirmation = this.OpponentConfirmation;
            obj.IsUnfinished         = this.IsUnfinished;
            obj.OpponentName         = this.OpponentName;
            obj.VenueID              = this.VenueID;
            obj.VenueName            = this.VenueName;
            obj.Date                 = this.Date;
            obj.TableSize            = this.TableSize;
            obj.MatchScoreA          = this.MatchScoreA;
            obj.MatchScoreB          = this.MatchScoreB;
            if (this.HasFrameScores)
            {
                obj.FrameScores = (from i in this.FrameScores
                                   select i.Clone()).ToList();
            }
            if (this.YourBreaks != null)
            {
                obj.YourBreaks = (from i in this.YourBreaks
                                  select i.Clone()).ToList();
            }
            if (this.OpponentBreaks != null)
            {
                obj.OpponentBreaks = (from i in this.OpponentBreaks
                                      select i.Clone()).ToList();
            }
            return(obj);
        }
Example #2
0
        public static SnookerMatchScore FromScore(int athleteID, Score score)
        {
            SnookerMatchScore match = new SnookerMatchScore();

            match.ID                = score.ScoreID;
            match.YourAthleteID     = score.AthleteAID;
            match.OpponentAthleteID = score.AthleteBID;
            match.VenueID           = score.VenueID ?? 0;
            match.Date              = score.Date;
            match.IsUnfinished      = score.IsUnfinished;
            if (score.Type1 == null)
            {
                match.TableSize = SnookerTableSizeEnum.Unknown;
            }
            else
            {
                match.TableSize = (SnookerTableSizeEnum)score.Type1.Value;
            }
            match.MatchScoreA          = score.PointsA;
            match.MatchScoreB          = score.PointsB;
            match.OpponentConfirmation = (OpponentConfirmationEnum)score.AthleteBConfirmation;

            match.FrameScores = new List <SnookerFrameScore>();
            for (int i = 1; i <= 10; ++i)
            {
                int a = score.InnerPointsA[i - 1];
                int b = score.InnerPointsB[i - 1];
                if (a > 0 || b > 0)
                {
                    match.FrameScores.Add(new SnookerFrameScore()
                    {
                        A = a, B = b
                    });
                }
            }

            if (score.AthleteBID == athleteID)
            {
                // invert all
                match.YourAthleteID     = score.AthleteBID;
                match.OpponentAthleteID = score.AthleteAID;
                match.MatchScoreA       = score.PointsB;
                match.MatchScoreB       = score.PointsA;
                foreach (var frame in match.FrameScores)
                {
                    var a = frame.A;
                    frame.A = frame.B;
                    frame.B = a;
                }
            }

            // breaks
            if (score.ExtraData != null)
            {
                try
                {
                    List <SnookerBreakDataCompressed> breaks = Newtonsoft.Json.JsonConvert.DeserializeObject <List <SnookerBreakDataCompressed> >(score.ExtraData);
                    match.YourBreaks     = new List <SnookerBreak>();
                    match.OpponentBreaks = new List <SnookerBreak>();
                    foreach (SnookerBreakDataCompressed compressed in breaks)
                    {
                        SnookerBreak snookerBreak = new SnookerBreak()
                        {
                            Date          = compressed.Date,
                            Points        = compressed.Points,
                            NumberOfBalls = compressed.Number,
                            Balls         = compressed.Balls.ToList(),
                            FrameNumber   = compressed.Frame,
                            IsFoul        = compressed.IsFoul
                        };
                        if (compressed.AthleteID == match.OpponentAthleteID)
                        {
                            snookerBreak.AthleteID         = match.OpponentAthleteID;
                            snookerBreak.OpponentAthleteID = match.YourAthleteID;
                            match.OpponentBreaks.Add(snookerBreak);
                        }
                        else
                        {
                            snookerBreak.AthleteID         = match.YourAthleteID;
                            snookerBreak.OpponentAthleteID = match.OpponentAthleteID;
                            match.YourBreaks.Add(snookerBreak);
                        }
                    }
                }
                catch (Exception)
                {
                    match.YourBreaks     = null;
                    match.OpponentBreaks = null;
                }
            }

            return(match);
        }
Example #3
0
        public SnookerFrameAnalysis Analyze(SnookerMatchScore match, int frameNumber)
        {
            SnookerFrameAnalysis analysis = new SnookerFrameAnalysis();

            analysis.Status = SnookerFrameAnalysisEnum.Issues;
            analysis.Issue  = "";

            // all breaks
            List <SnookerBreak> breaks = match.GetBreaksForFrame(frameNumber).OrderBy(i => i.Date).ToList();

            // do the frame scores total the breaks?
            if (match.FrameScores == null || frameNumber < match.FrameScores.Count)
            {
                analysis.Status = SnookerFrameAnalysisEnum.NotFullyTracked;
                analysis.Issue  = "No frame scores";
                return(analysis);
            }
            SnookerFrameScore frameScore = match.FrameScores[frameNumber - 1];
            int pointsA = breaks.Where(i => i.AthleteID == match.YourAthleteID).Sum(i => i.Points);
            int pointsB = breaks.Where(i => i.AthleteID == match.OpponentAthleteID).Sum(i => i.Points);

            if (frameScore.A != pointsA || frameScore.B != pointsB)
            {
                analysis.Status = SnookerFrameAnalysisEnum.NotFullyTracked;
                analysis.Issue  = "Frame score edited";
                return(analysis);
            }

            // score difference
            int scoreDifference = System.Math.Abs(frameScore.A - frameScore.B);

            analysis.ScoreDifference = scoreDifference;

            /// go thru the breaks
            ///
            int numberOfRedsLeft        = 15;
            int numberOfFouls           = 0;
            int lastColoredPocketedBall = 1;

            foreach (var b in breaks)
            {
                int index = breaks.IndexOf(b) + 1;

                if (b.NumberOfBalls < 1)
                {
                    analysis.Issue = "Empty break #" + index;
                    return(analysis);
                }

                if (b.NumberOfBalls == 1 && b.Points >= 4 && b.Points <= 7)
                {
                    numberOfFouls++;
                    continue;
                }

                bool expectingColoredAfterRed = false;
                for (int i = 0; i < b.Balls.Count; ++i)
                {
                    int ball = b.Balls[i];
                    if (numberOfRedsLeft > 0 || expectingColoredAfterRed)
                    {
                        // red, colored, red, colored

                        if (expectingColoredAfterRed == true && ball == 1)
                        {
                            if (numberOfRedsLeft <= 0)
                            {
                                analysis.Issue = "Invalid break #" + index;
                                return(analysis);
                            }

                            // several reds at the same time (happens when more than one red pocketed at the same time)
                            numberOfRedsLeft--;
                            continue;
                        }

                        if (expectingColoredAfterRed)
                        {
                            if (ball < 2 || ball > 7)
                            {
                                analysis.Issue = "Invalid break #" + index;
                                return(analysis);
                            }
                            expectingColoredAfterRed = false;
                        }
                        else
                        {
                            if (ball != 1)
                            {
                                analysis.Issue = "Invalid break #" + index;
                                return(analysis);
                            }

                            numberOfRedsLeft--;
                            expectingColoredAfterRed = true;
                        }
                    }
                    else
                    {
                        // last colored

                        if (ball < 2 || ball > 7)
                        {
                            analysis.Issue = "Invalid break #" + index;
                            return(analysis);
                        }

                        if (ball > lastColoredPocketedBall + 1 || ball == lastColoredPocketedBall)
                        {
                            numberOfFouls++;
                            continue;
                        }

                        if (ball != lastColoredPocketedBall + 1)
                        {
                            analysis.Issue = "Invalid break #" + index;
                            return(analysis);
                        }

                        lastColoredPocketedBall = ball;

                        if (ball == 7)
                        {
                            bool ok = false;
                            if (i == b.Balls.Count - 1)
                            {
                                ok = true;
                            }
                            if (i == b.Balls.Count - 2 && b.Balls[i + 1] == 7)
                            {
                                ok = true;
                            }
                            if (ok == false)
                            {
                                analysis.Issue = "Breaks after last ball potted";
                                return(analysis);
                            }
                        }
                    }
                }
            }

            /// Calculate number of points left
            ///
            int numberOfLastColoredBallPointsLeft = 0; // maximum=2+3+4+5+6+7=27

            for (int ball = 7; ball >= 2; --ball)
            {
                if (ball <= lastColoredPocketedBall)
                {
                    break;
                }
                numberOfLastColoredBallPointsLeft += ball;
            }
            int numberOfPointsLeft = numberOfLastColoredBallPointsLeft;

            numberOfPointsLeft += numberOfRedsLeft * (1 + 7);

            /// Calculate snookers required
            ///
            int snookersRequired = 0;

            if (numberOfPointsLeft < scoreDifference)
            {
                int snookerPoints = 4;
                if (lastColoredPocketedBall > 4)
                {
                    snookerPoints = lastColoredPocketedBall;
                }
                int extraPoints = scoreDifference - numberOfPointsLeft;
                snookersRequired = extraPoints / snookerPoints;
                if (extraPoints % snookerPoints > 0)
                {
                    snookersRequired++;
                }
            }

            analysis.Status             = SnookerFrameAnalysisEnum.FullyTracked;
            analysis.Issue              = "";
            analysis.NumberOfBreaks     = breaks.Count - numberOfFouls;
            analysis.NumberOfFouls      = numberOfFouls;
            analysis.NumberOfRedsLeft   = numberOfRedsLeft;
            analysis.NumberOfPointsLeft = numberOfPointsLeft;
            analysis.SnookersRequired   = snookersRequired;
            return(analysis);
        }