예제 #1
0
        public static Tuple <int, Position> ParseStoneRemoval(IgsLine igsLine)
        {
            Match match = regexStoneRemoval.Match(igsLine.EntireLine);

            return(new Tuple <int, Position>(match.Groups[1].Value.AsInteger(),
                                             Position.FromIgsCoordinates(match.Groups[3].Value)));
        }
예제 #2
0
        public static ChatMessage ParseSayLine(IgsLine igsLine, IgsConnection server)
        {
            Match match = regexSay.Match(igsLine.EntireLine);

            return(new ChatMessage(match.Groups[1].Value, match.Groups[2].Value, DateTimeOffset.Now,
                                   match.Groups[1].Value == server.Username ? ChatMessageKind.Outgoing : ChatMessageKind.Incoming));
        }
예제 #3
0
        /// <summary>
        /// Attempts to parse a line as an IGS game heading starting with the code 15. If it fails, it returns null.
        /// </summary>
        /// <param name="line">The line, such as "15 Game 693 I: Robot730 (0 4500 -1) vs OmegaGo3 (0 4500 -1)".</param>
        /// <returns></returns>
        public static GameHeading ParseGameHeading(IgsLine line)
        {
            Match match = regexGameHeading.Match(line.EntireLine);

            if (match.Success)
            {/*empty string
             *  1. 352
             *  2. SANYOSHI
             *  3. 0
             *  4. 849
             *  5. 13 (or -1)
             *  6. hamas5ngo
             *  7. 0
             *  8. 900
             *  9. 25
             *  empty string*/
                CanadianTimeInformation black = IgsRegex.TimeInformationFromGameHeading(
                    match.Groups[8].Value.AsInteger(),
                    match.Groups[9].Value.AsInteger());
                CanadianTimeInformation white = IgsRegex.TimeInformationFromGameHeading(
                    match.Groups[4].Value.AsInteger(),
                    match.Groups[5].Value.AsInteger());
                return(new GameHeading(
                           match.Groups[1].Value.AsInteger(),
                           match.Groups[2].Value,
                           match.Groups[6].Value,
                           black,
                           white));
            }
            return(null);
        }
예제 #4
0
        public static Tuple <string, int> ParseKibitzHeading(IgsLine igsLine)
        {
            Match match = regexKibitzHeading.Match(igsLine.EntireLine);

            return(new Tuple <string, int>(
                       match.Groups[1].Value,
                       match.Groups[2].Value.AsInteger()
                       ));
        }
예제 #5
0
        public static ScoreLine ParseScoreLine(IgsLine scoreLine)
        {
            Match match = regexScoreLine.Match(scoreLine.EntireLine);

            return(new ScoreLine(match.Groups[1].Value,
                                 match.Groups[3].Value,
                                 match.Groups[4].Value.AsFloat(),
                                 match.Groups[2].Value.AsFloat(),
                                 -1));
        }
예제 #6
0
 internal static int ParseGameNumberFromHeading(IgsLine igsLine)
 {
     // 15 Game 10 I: Soothie (0 4500 -1) vs OmegaGo1 (0 4500 -1)
     if (igsLine.PureLine.StartsWith("Game "))
     {
         string trim2      = igsLine.PureLine.Substring("Game ".Length);
         int    gameNumber = int.Parse(trim2.Substring(0, trim2.IndexOf(' ')));
         return(gameNumber);
     }
     throw new ArgumentException("That's not a valid input.");
 }
예제 #7
0
        internal static string ParseTitleInformation(IgsLine titleLine)
        {
            Match match = regexGameTitleLine.Match(titleLine.EntireLine);

            if (match.Success)
            {
                string fullName = match.Groups[1].Value;
                return(fullName);
            }
            else
            {
                return(null);
            }
        }
예제 #8
0
        public static IgsMatchRequest ParseMatchRequest(IgsLine line)
        {
            Match match = regexMatchRequest.Match(line.EntireLine);

            if (match.Success)
            {
                return(IgsMatchRequest.FromOldStyleResponse(match.Groups[1].Value,
                                                            match.Groups[2].Value == "B" ? StoneColor.Black : StoneColor.White,
                                                            match.Groups[3].Value.AsInteger(),
                                                            match.Groups[4].Value.AsInteger(),
                                                            match.Groups[5].Value.AsInteger()));
            }
            return(null);
        }
        private void HandleIncomingMove(IgsLine igsLine)
        {
            string      trim    = igsLine.PureLine.Trim();
            GameHeading heading = IgsRegex.ParseGameHeading(igsLine);

            if (heading != null)
            {
                IgsGame whatGame = this.GamesYouHaveOpened.Find(gm => gm.Info.IgsIndex == heading.GameNumber);
                if (whatGame == null)
                {
                    // Do not remember this game, perhaps we're in match accept procedure
                    return;
                }
                _incomingMovesAreForThisGame = whatGame;
                GetConnector(whatGame.Info).TimeControlAdjustment(new IgsTimeControlAdjustmentEventArgs(heading.WhiteTimeRemaining, heading.BlackTimeRemaining));
            }
            else if (trim.Contains("Handicap"))
            {
                //  15   0(B): Handicap 3
                int handicapStones = IgsRegex.ParseHandicapMove(igsLine);
                OnIncomingHandicapInformation(_incomingMovesAreForThisGame, handicapStones);
            }
            else
            {
                Match      match       = this._regexMove.Match(trim);
                string     moveIndex   = match.Groups[1].Value;
                string     mover       = match.Groups[2].Value;
                string     coordinates = match.Groups[3].Value;
                string     captures    = match.Groups[4].Value;
                StoneColor moverColor  = mover == "B" ? StoneColor.Black : StoneColor.White;
                Move       move;
                if (coordinates == "Pass")
                {
                    move = Move.Pass(moverColor);
                }
                else
                {
                    move = Move.PlaceStone(moverColor,
                                           Position.FromIgsCoordinates(coordinates));
                }
                string[] captureSplit = captures.Split(new[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
                foreach (string capture in captureSplit)
                {
                    move.Captures.Add(Position.FromIgsCoordinates(capture));
                }
                HandleIncomingMove(_incomingMovesAreForThisGame, int.Parse(moveIndex), move);
            }
        }
예제 #10
0
        public static ScoreLine ParseObservedScoreLine(IgsLine infoLine)
        {
            Match match = regexObservedScoreLine.Match(infoLine.EntireLine);

            if (match.Success)
            {
                return(new ScoreLine(match.Groups[2].Value,
                                     match.Groups[3].Value,
                                     match.Groups[5].Value.AsFloat(),
                                     match.Groups[4].Value.AsFloat(),
                                     match.Groups[1].Value.AsInteger()));
            }
            else
            {
                return(null);
            }
        }
예제 #11
0
        /// <summary>
        /// The returned task waits until the IGS SERVER sends all the response data to our command, terminated by a prompt line, and then
        /// it returns this data as a <see cref="List{T}"/>.
        /// </summary>
        public async Task <IgsResponse> GetAllLines()
        {
            IgsResponse lines = new IgsResponse();

            while (true)
            {
                IgsLine line = await IncomingLines.ReceiveAsync();

                if (ForgottenForever)
                {
                    throw new System.Exception("If this happens, we should examine this in detail.");
                }
                if (line.Code == IgsCode.Prompt)
                {
                    break;
                }
                lines.Add(line);
            }
            return(lines);
        }
        private async void HandleFullInterrupt(List <IgsLine> currentLineBatch)
        {
            if (currentLineBatch.Count > 0)
            {
                if (currentLineBatch.Any(line => line.Code == IgsCode.Status))
                {
                    var infoLine = currentLineBatch.FirstOrDefault(ln => ln.Code == IgsCode.Info);
                    if (infoLine != null)
                    {
                        ScoreLine scoreLine = IgsRegex.ParseObservedScoreLine(infoLine);
                        if (scoreLine != null)
                        {
                            IgsGame gameInfo = this.GamesYouHaveOpened.FirstOrDefault(gi => gi.Info.IgsIndex == scoreLine.GameId);
                            if (gameInfo != null)
                            {
                                ScoreGame(gameInfo, scoreLine.BlackScore, scoreLine.WhiteScore);
                            }
                        }
                    }
                }
                if (currentLineBatch.Any(line => line.PureLine.EndsWith("accepted.") && line.Code == IgsCode.Info))
                {
                    // An outgoing match request has been accepted by another player and the game can begin.
                    GameHeading heading = this.Data.LastReceivedGameHeading;
                    var         ogi     = await Commands.GetGameByIdAsync(heading.GameNumber);

                    var  builder     = GameBuilder.CreateOnlineGame(ogi).Connection(this);
                    bool youAreBlack = ogi.Black.Name == _username;
                    bool youAreWhite = ogi.White.Name == _username;
                    if (youAreBlack)
                    {
                        builder.BlackPlayer(
                            new HumanPlayerBuilder(StoneColor.Black)
                            .Name(ogi.Black.Name)
                            .Rank(ogi.Black.Rank)
                            .Clock(new CanadianTimeControl(TimeSpan.Zero, 25, TimeSpan.FromMinutes(ogi.ByoyomiPeriod)).UpdateFrom(heading.BlackTimeRemaining))
                            .Build());
                    }
                    else
                    {
                        builder.BlackPlayer(
                            new IgsPlayerBuilder(StoneColor.Black, this)
                            .Name(ogi.Black.Name)
                            .Rank(ogi.Black.Rank)
                            .Clock(new CanadianTimeControl(TimeSpan.Zero, 25, TimeSpan.FromMinutes(ogi.ByoyomiPeriod)).UpdateFrom(heading.BlackTimeRemaining))
                            .Build());
                    }
                    if (youAreWhite)
                    {
                        builder.WhitePlayer(
                            new HumanPlayerBuilder(StoneColor.White)
                            .Name(ogi.White.Name)
                            .Rank(ogi.White.Rank)
                            .Clock(new CanadianTimeControl(TimeSpan.Zero, 25, TimeSpan.FromMinutes(ogi.ByoyomiPeriod)).UpdateFrom(heading.WhiteTimeRemaining))
                            .Build());
                    }
                    else
                    {
                        builder.WhitePlayer(
                            new IgsPlayerBuilder(StoneColor.White, this)
                            .Name(ogi.White.Name)
                            .Rank(ogi.White.Rank)
                            .Clock(new CanadianTimeControl(TimeSpan.Zero, 25, TimeSpan.FromMinutes(ogi.ByoyomiPeriod)).UpdateFrom(heading.WhiteTimeRemaining))
                            .Build());
                    }
                    IgsGame newGame = builder.Build();
                    this.GamesYouHaveOpened.Add(newGame);
                    Events.OnMatchRequestAccepted(newGame);
                }

                if (currentLineBatch.Any(line => line.PureLine.Contains("Creating match") && line.Code == IgsCode.Info))
                {
                    // Make it not be an interrupt and let it be handled by the match creator.
                    foreach (IgsLine line in currentLineBatch)
                    {
                        lock (this._mutex)
                        {
                            if (this._requestInProgress != null)
                            {
                                this._requestInProgress.IncomingLines.Post(line);
                            }
                            else
                            {
                                if (this.Composure == IgsComposure.Ok)
                                {
                                    Events.OnUnhandledLine(line.EntireLine);
                                }
                            }
                        }
                    }
                }

                if (currentLineBatch.Count == 3 && currentLineBatch[0].Code == IgsCode.SayInformation &&
                    currentLineBatch[1].Code == IgsCode.Say)
                {
                    int         gameNumber   = IgsRegex.ParseGameNumberFromSayInformation(currentLineBatch[0]);
                    ChatMessage chatLine     = IgsRegex.ParseSayLine(currentLineBatch[1], this);
                    IgsGame     relevantGame = this.GamesYouHaveOpened.Find(gi => gi.Info.IgsIndex == gameNumber);
                    if (relevantGame == null)
                    {
                        // We received a chat message for a game we no longer play.
                        return;
                    }
                    if (chatLine.Text.StartsWith(gameNumber + " "))
                    {
                        chatLine.Text = chatLine.Text.Substring((gameNumber + " ").Length);
                    }

                    GetConnector(relevantGame.Info).ChatMessageFromServer(chatLine);
                }

                if (currentLineBatch[0].Code == IgsCode.Kibitz &&
                    currentLineBatch.Count >= 2)
                {
                    // 11 Kibitz ([^ ]+).*\[([0-9]+)\]
                    Tuple <string, int> firstLine = IgsRegex.ParseKibitzHeading(currentLineBatch[0]);
                    string  text         = currentLineBatch[1].PureLine.Trim();
                    IgsGame relevantGame = this.GamesYouHaveOpened.Find(gi => gi.Info.IgsIndex == firstLine.Item2);
                    GetConnector(relevantGame.Info).ChatMessageFromServer(new ChatMessage(firstLine.Item1,
                                                                                          text, DateTimeOffset.Now, firstLine.Item1 == this.Username ? ChatMessageKind.Outgoing : ChatMessageKind.Incoming));
                }

                if (currentLineBatch[0].Code == IgsCode.Tell &&
                    currentLineBatch[0].PureLine.StartsWith("*SYSTEM*") &&
                    currentLineBatch[0].PureLine.EndsWith("requests undo."))
                {
                    string requestingUser = IgsRegex.WhoRequestsUndo(currentLineBatch[0]);
                    var    games          = GetGamesIncluding(requestingUser);
                    if (games.Any())
                    {
                        foreach (var game in games)
                        {
                            Events.OnUndoRequestReceived(game.Info);
                        }
                    }
                    else
                    {
                        throw new Exception("Received an undo request for a game that's not in progress.");
                    }
                    this._ignoreNextPrompt = true;
                }
                if (currentLineBatch[0].Code == IgsCode.Undo)
                {
                    int     numberOfMovesToUndo = currentLineBatch.Count(line => line.Code == IgsCode.Undo);
                    IgsLine gameHeadingLine     = currentLineBatch.Find(line => line.Code == IgsCode.Move);
                    int     game     = IgsRegex.ParseGameNumberFromHeading(gameHeadingLine);
                    IgsGame gameInfo = this.GamesYouHaveOpened.Find(gi => gi.Info.IgsIndex == game);
                    for (int i = 0; i < numberOfMovesToUndo; i++)
                    {
                        GetConnector(gameInfo.Info).ForceMainUndo();
                    }
                }

                if (currentLineBatch[0].EntireLine.Contains("'done'"))
                {
                    IgsLine gameHeadingLine = currentLineBatch.Find(line => line.Code == IgsCode.Move);
                    int     gameIndex       = IgsRegex.ParseGameNumberFromHeading(gameHeadingLine);
                    _availableConnectors[gameIndex].SetPhaseFromServer(GamePhaseType.LifeDeathDetermination);
                }
                if (currentLineBatch.Any(ln => ln.Code == IgsCode.Score))
                {
                    ScoreLine scoreLine = IgsRegex.ParseScoreLine(currentLineBatch.Find(ln => ln.Code == IgsCode.Score));
                    IgsGame   gameInfo  = this.GamesYouHaveOpened.Find(gi =>
                                                                       gi.Info.White.Name == scoreLine.White &&
                                                                       gi.Info.Black.Name == scoreLine.Black);
                    ScoreGame(gameInfo, scoreLine.BlackScore, scoreLine.WhiteScore);
                }
            }
        }
        private async Task HandleIncomingData(StreamReader sr)
        {
            bool           thisIsNotAMove           = false;
            bool           weAreHandlingAnInterrupt = false;
            bool           interruptIsImpossible    = false;
            List <IgsLine> currentLineBatch         = new List <IgsLine>();

            while (true)
            {
                string line;
                try
                {
                    line = await sr.ReadLineAsync();
                }
                catch (Exception)
                {
                    line = null;
                }
                if (line == null)
                {
                    ConnectionLost();
                    return;
                }
                line = line.Trim();


                IgsCode code    = ExtractCodeFromLine(line);
                IgsLine igsLine = new IgsLine(code, line);
                Events.OnIncomingLine((weAreHandlingAnInterrupt ? "(INTERRUPT) " : "") + (interruptIsImpossible ? "(INTERRUPT IMPOSSIBLE) " : "") + line);

                // IGS occasionally sends blank lines, I don't know why. They serve no reason.
                if (line == "")
                {
                    continue;
                }

                switch (this.Composure)
                {
                case IgsComposure.Confused:
                case IgsComposure.Ok:
                case IgsComposure.Disconnected:
                    // No special mode.
                    break;

                case IgsComposure.InitialHandshake:
                    if (igsLine.EntireLine.Trim() == "1 5")
                    {
                        this.Composure = IgsComposure.Ok;
                        continue;
                    }
                    else
                    {
                        // Ignore.
                        continue;
                    }

                case IgsComposure.LoggingIn:
                    if (igsLine.EntireLine.Contains("Invalid password."))
                    {
                        this.Composure   = IgsComposure.Confused;
                        this._loginError = "The password is incorrect.";
                        continue;
                    }
                    if (igsLine.EntireLine.Contains("Sorry, names can be"))
                    {
                        this.Composure   = IgsComposure.Confused;
                        this._loginError = "Your name is too long.";
                        continue;
                    }
                    if (igsLine.EntireLine.Contains("This is a guest account."))
                    {
                        this.Composure   = IgsComposure.Confused;
                        this._loginError = "The username does not exist.";
                        continue;
                    }
                    if (igsLine.EntireLine.Contains("1 5"))
                    {
                        this.Composure = IgsComposure.Ok;
                        continue;
                    }
                    break;
                }

                if (igsLine.Code == IgsCode.Error)
                {
                    Events.OnErrorMessageReceived(igsLine.PureLine);
                }
                currentLineBatch.Add(igsLine);

                if (weAreHandlingAnInterrupt && code == IgsCode.Prompt)
                {
                    // Interrupt message is over, let's wait for a new message
                    weAreHandlingAnInterrupt = false;
                    HandleFullInterrupt(currentLineBatch);
                    thisIsNotAMove        = false;
                    interruptIsImpossible = false;
                    currentLineBatch      = new List <IgsLine>();
                    continue;
                }
                if (code == IgsCode.Prompt)
                {
                    thisIsNotAMove        = false;
                    currentLineBatch      = new List <IgsLine>();
                    interruptIsImpossible = false;
                    if (this._ignoreNextPrompt)
                    {
                        this._ignoreNextPrompt = false;
                        continue;
                    }
                }
                if (code == IgsCode.Kibitz)
                {
                    weAreHandlingAnInterrupt = true;
                    continue;
                }
                if (code == IgsCode.Beep)
                {
                    Events.OnBeep();
                    continue;
                }

                if (!interruptIsImpossible)
                {
                    if (code == IgsCode.Tell)
                    {
                        if (igsLine.PureLine.StartsWith("*SYSTEM*"))
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        HandleIncomingChatMessage(line);
                        weAreHandlingAnInterrupt = true;
                        continue;
                    }
                    if (code == IgsCode.SayInformation)
                    {
                        weAreHandlingAnInterrupt = true;
                        continue;
                    }
                    if (code == IgsCode.Status)
                    {
                        weAreHandlingAnInterrupt = true;
                        continue;
                    }
                    if (code == IgsCode.Shout)
                    {
                        HandleIncomingShoutMessage(line);
                        weAreHandlingAnInterrupt = true;
                        continue;
                    }
                    if (code == IgsCode.StoneRemoval)
                    {
                        Tuple <int, Position> removedStone = IgsRegex.ParseStoneRemoval(igsLine);
                        OnIncomingStoneRemoval(removedStone.Item1, removedStone.Item2);
                        continue;
                    }
                    if (code == IgsCode.Move)
                    {
                        var heading = IgsRegex.ParseGameHeading(igsLine);
                        if (heading != null)
                        {
                            this.Data.LastReceivedGameHeading = heading;
                        }
                        if (!thisIsNotAMove)
                        {
                            HandleIncomingMove(igsLine);
                            weAreHandlingAnInterrupt = true;
                        }
                        continue;
                    }
                    if (code == IgsCode.Undo)
                    {
                        thisIsNotAMove           = true;
                        weAreHandlingAnInterrupt = true;
                        continue;
                    }
                }
                if (code == IgsCode.Info)
                {
                    // 9 Adding game to observation list.
                    if (igsLine.EntireLine.Contains("9 Adding game to observation list."))
                    {
                        interruptIsImpossible = true;
                    }
                    if (!interruptIsImpossible)
                    {
                        if (igsLine.PureLine == "yes")
                        {
                            // This is "ayt" response, ignore it.
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }

                        if (igsLine.EntireLine ==
                            "9 You can check your score with the score command, type 'done' when finished.")
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("accepted."))
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("Removing @"))
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("has run out of time"))
                        {
                            weAreHandlingAnInterrupt = true;
                            string whoRanOutOfTime = IgsRegex.WhoRanOutOfTime(igsLine);
                            foreach (var game in GetGamesIncluding(whoRanOutOfTime).ToList())
                            {
                                game.Controller.IgsConnector.EndTheGame(
                                    GameEndInformation.CreateTimeout(
                                        game.Controller.Players.First(pl => pl.Info.Name == whoRanOutOfTime),
                                        game.Controller.Players)
                                    );
                            }
                            continue;
                        }
                        if (igsLine.PureLine.Contains("White resigns.}"))
                        {
                            int gameInWhichSomebodyResigned = IgsRegex.WhatObservedGameWasResigned(igsLine);
                            ResignObservedGame(gameInWhichSomebodyResigned, StoneColor.White);
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("Black resigns.}"))
                        {
                            int gameInWhichSomebodyResigned = IgsRegex.WhatObservedGameWasResigned(igsLine);
                            ResignObservedGame(gameInWhichSomebodyResigned, StoneColor.Black);
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("has resigned the game"))
                        {
                            string whoResigned = IgsRegex.WhoResignedTheGame(igsLine);
                            if (whoResigned != this._username)
                            {
                                // .ToList() is used because the collection may be modified
                                foreach (var game in GetGamesIncluding(whoResigned).ToList())
                                {
                                    HandleIncomingResignation(game.Info, whoResigned);
                                }
                            }
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("has typed done."))
                        {
                            string username = IgsRegex.GetFirstWord(igsLine);
                            weAreHandlingAnInterrupt = true;
                            foreach (var game in GetGamesIncluding(username))
                            {
                                var player = game.Controller.Players.First(pl => pl.Info.Name == username);
                                game.Controller.IgsConnector.RaiseServerSaidDone(player);
                            }
                            continue;
                        }
                        if (igsLine.PureLine.Contains("Board is restored to what it was when you started scoring"))
                        {
                            foreach (
                                var game in
                                this.GamesYouHaveOpened.Where(
                                    gi =>
                                    gi.Controller.Phase.Type ==
                                    GamePhaseType.LifeDeathDetermination))
                            {
                                GetConnector(game.Info).ForceLifeDeathUndoDeathMarks();
                            }
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }

                        if (igsLine.PureLine.Contains("Removed game file"))
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.Contains("game completed."))
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.StartsWith("!!*Pandanet*!!:"))
                        {
                            // Advertisement
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (IgsRegex.IsIrrelevantInterruptLine(igsLine))
                        {
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                        if (igsLine.PureLine.StartsWith("Increase "))
                        {
                            weAreHandlingAnInterrupt = true;
                            string person = IgsRegex.ParseIncreaseXTimeByYMinute(igsLine);
                            foreach (var game in this.GamesYouHaveOpened)
                            {
                                if (game.Info.Black.Name == person ||
                                    game.Info.White.Name == person)
                                {
                                    MakeUnattendedRequest("refresh " + game.Info.IgsIndex);
                                }
                            }
                        }

                        if (igsLine.PureLine.EndsWith("declines undo."))
                        {
                            string username = IgsRegex.WhoDeclinesUndo(igsLine);
                            foreach (var game in GetGamesIncluding(username))
                            {
                                Events.OnUndoDeclined(game.Info);
                            }
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }

                        if (igsLine.PureLine.EndsWith("declines your request for a match."))
                        {
                            Events.OnMatchRequestDeclined(igsLine.PureLine.Substring(0, igsLine.PureLine.IndexOf(' ')));
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }

                        IgsMatchRequest matchRequest = IgsRegex.ParseMatchRequest(igsLine);
                        if (matchRequest != null)
                        {
                            this._incomingMatchRequests.Add(matchRequest);
                            Events.OnIncomingMatchRequest(matchRequest);
                            weAreHandlingAnInterrupt = true;
                            continue;
                        }
                    }
                }

                if (!weAreHandlingAnInterrupt)
                {
                    // We cannot handle this generally - let's hand it off to whoever made the request for this information.
                    lock (this._mutex)
                    {
                        if (this._requestInProgress != null)
                        {
                            this._requestInProgress.IncomingLines.Post(igsLine);
                        }
                        else
                        {
                            if (this.Composure == IgsComposure.Ok)
                            {
                                Events.OnUnhandledLine(igsLine.EntireLine);
                            }
                        }
                    }
                }
            }
        }
예제 #14
0
 /// <summary>
 /// From a line such as '9 Increase OmegaGo2's time by 1096 minutes', extracts 'OmegaGo2'.
 /// </summary>
 /// <param name="line">The incoming instruction.</param>
 /// <returns></returns>
 public static string ParseIncreaseXTimeByYMinute(IgsLine line)
 {
     return(regexIncreaseTime.Match(line.EntireLine).Groups[1].Value);
 }
예제 #15
0
        public static int ParseGameNumberFromSayInformation(IgsLine igsLine)
        {
            Match match = regexSayInformation.Match(igsLine.EntireLine);

            return(match.Groups[1].Value.AsInteger());
        }
예제 #16
0
 // http://regexstorm.net/tester
 public static bool IsIrrelevantInterruptLine(IgsLine line)
 {
     return(line.Code == IgsCode.Info && line.PureLine.StartsWith("Match[") &&
            line.PureLine.Contains("requested with"));
 }
예제 #17
0
 /// <summary>
 /// Gets the number of handicap stones to place down, under Japanese rules, from a line such as '15   0(B): Handicap 3'.
 /// </summary>
 public static int ParseHandicapMove(IgsLine igsLine)
 {
     return(regexHandicapMove.Match(igsLine.EntireLine).Groups[1].Value.AsInteger());
 }
예제 #18
0
        public static int WhatObservedGameWasResigned(IgsLine igsLine)
        {
            Match match = regexWhatObservedGameWasResigned.Match(igsLine.EntireLine);

            return(match.Groups[1].Value.AsInteger());
        }
예제 #19
0
        public static string WhoDeclinesUndo(IgsLine igsLine)
        {
            Match match = regexUndoDecline.Match(igsLine.EntireLine);

            return(match.Groups[1].Value);
        }
예제 #20
0
        public static string WhoRanOutOfTime(IgsLine igsLine)
        {
            Match match = regexHasRunOutOfTime.Match(igsLine.EntireLine);

            return(match.Groups[1].Value);
        }
예제 #21
0
 public static string WhoResignedTheGame(IgsLine igsLine)
 {
     return(regexHasResignedTheGame.Match(igsLine.EntireLine).Groups[1].Value);
 }
예제 #22
0
 public static string GetFirstWord(IgsLine igsLine)
 {
     return(igsLine.PureLine.Substring(0, igsLine.PureLine.IndexOf(' ')));
 }