Beispiel #1
0
        /// <summary>
        /// Executes the requested bake operation.
        /// </summary>
        /// <param name="player"></param>
        /// <param name="data"></param>
        public static void Bake(AgricolaPlayer player, ImmutableList <GameEventTrigger> eventTriggers, List <GameActionNotice> resultingNotices, ImmutableArray <ResourceConversionData> data)
        {
            if (data != null && data.Length > 0)
            {
                var bakeInput  = new ResourceCache(Resource.Grain, 0);
                var bakeOutput = new ResourceCache(Resource.Food, 0);
                foreach (var bake in data)
                {
                    var card      = ((AgricolaGame)player.Game).GetCard(bake.Id);
                    var resources = Curator.GetBakeOutput(player, bake.Id, bake.Count);
                    if (resources != null)
                    {
                        player.AddResource(card.BakeProperties.InType, -bake.Count);
                        player.AddResource(resources);

                        bakeInput  = bakeInput.updateCount(bake.Count);
                        bakeOutput = bakeOutput.updateCount(resources.Count);
                    }
                }

                resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.Bake.ToString(), new ConversionPredicate(bakeInput, bakeOutput)));

                var trigger = new BakeTrigger(bakeInput.Count);
                ProcessEventTrigger(player, trigger, resultingNotices);
                CheckTriggers(player, eventTriggers, resultingNotices);
            }
        }
Beispiel #2
0
        /// <summary>
        /// Puts an occupation into player for the given player. After all custom event triggers are fired,
        /// a PlayOccupationTrigger will be fired.
        /// </summary>
        /// <param name="player">The player who owns the occupation</param>
        /// <param name="eventTriggers">Any triggers that should be fired when this occupation is played</param>
        /// <param name="resultingNotices">A list of notices that should be sent to players</param>
        /// <param name="data">The data for the occupation being played</param>
        public static void PlayOccupation(AgricolaPlayer player, ImmutableList <GameEventTrigger> eventTriggers, List <GameActionNotice> resultingNotices, OccupationActionData data)
        {
            var card = ((AgricolaGame)player.Game).GetCard(data.Id.Value);
            var cost = Curator.GetOccupationCost(player, data.ActionId, data.Id.Value);

            foreach (var resource in cost)
            {
                player.AddResource(resource.Type, -resource.Count);
            }
            player.PlayCard(data.Id.Value);

            foreach (var evnt in card.OnPlayEvents)
            {
                evnt.Execute(player, null, card, resultingNotices);
            }

            resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.PlayOccupation.ToString(), new IdPredicate(data.Id.Value)));

            CheckTriggers(player, eventTriggers, resultingNotices);


            var trigger = new PlayOccupationTrigger(card);

            ProcessEventTrigger(player, trigger, resultingNotices);
        }
Beispiel #3
0
        /// <summary>
        /// Assigns a single resource to a player.
        /// This method triggers no events.
        /// </summary>
        /// <param name="player"></param>
        /// <param name="resource"></param>
        /// <param name="resultingNotices"></param>
        public static void AssignResource(AgricolaPlayer player, ResourceCache resource, List <GameActionNotice> resultingNotices)
        {
            player.AddResource(resource);
            var resourcePredicateFound = false;

            foreach (var predicates in resultingNotices.Where(x => ((string)x.Subject) == player.Name).Select(x => x.Predicates))
            {
                if (predicates != null)
                {
                    for (var i = 0; i < predicates.Count; i++)
                    {
                        var predicate = predicates[i];
                        if (predicate is ResourceCache)
                        {
                            resourcePredicateFound = true;
                            var cache = (ResourceCache)predicate;
                            if (cache.Type == resource.Type)
                            {
                                predicates[i] = cache.updateCount(resource.Count);
                                return;
                            }
                        }
                    }

                    if (resourcePredicateFound)
                    {
                        predicates.Add(new ResourceCache(resource.Type, resource.Count));
                        return;
                    }
                }
            }
            resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.Take.ToString(), new ResourceCache(resource.Type, resource.Count)));
        }
Beispiel #4
0
        public static void Sow(AgricolaPlayer player, ImmutableArray <SowData> sowData, List <GameActionNotice> resultingNotices)
        {
            if (sowData.Length > 0)
            {
                var grains     = 0;
                var vegetables = 0;
                foreach (var sow in sowData)
                {
                    player.AddResource(sow.Type, -1);
                    player.SowField(sow.Index, sow.Type);

                    if (sow.Type == Resource.Grain)
                    {
                        grains++;
                    }
                    if (sow.Type == Resource.Vegetables)
                    {
                        vegetables++;
                    }
                }

                var sowPredicates = new List <INoticePredicate>();
                if (grains > 0)
                {
                    sowPredicates.Add(new ResourceCache(Resource.Grain, grains));
                }
                if (vegetables > 0)
                {
                    sowPredicates.Add(new ResourceCache(Resource.Vegetables, vegetables));
                }

                resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.Sow.ToString(), sowPredicates));
            }
        }
Beispiel #5
0
        public static void Cook(AgricolaPlayer player, ImmutableList <GameEventTrigger> eventTriggers, ResourceConversionData[] data, List <GameActionNotice> resultingNotices)
        {
            var availableConversions = Curator.GetAnytimeResourceConversions(player);

            var trigger = new ResourceConversionTrigger();

            foreach (var conversion in data)
            {
                var conversionDefinition = availableConversions.Where(x => x.Id == conversion.Id &&
                                                                      x.InType == conversion.InType && x.InAmount == conversion.InAmount &&
                                                                      x.OutType == conversion.OutType).OrderByDescending(a => a.OutAmount).FirstOrDefault();


                if (!conversionDefinition.InType.IsAnimal())
                {
                    var inputCache  = new ResourceCache(conversionDefinition.InType, -conversion.Count);
                    var outputCache = new ResourceCache(conversionDefinition.OutType, (conversion.Count / conversionDefinition.InAmount) * conversionDefinition.OutAmount);
                    // Deduct the cost
                    player.AddResource(inputCache);

                    if (!conversionDefinition.OutType.IsAnimal())
                    {
                        // Add the converted resources
                        player.AddResource(outputCache);
                    }
                    else
                    {
                        ((AgricolaGame)player.Game).AddInterrupt(new AssignAnimalsAction(player, (AnimalResource)conversionDefinition.OutType, conversionDefinition.OutAmount, resultingNotices));
                    }

                    inputCache = new ResourceCache(inputCache.Type, inputCache.Count * -1);
                    resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.Converted.ToString(), new ConversionPredicate(inputCache, outputCache)));

                    trigger.AddConvertedResources(ResourcesConvertedData.FromResourceConversion(conversionDefinition, conversion.Count / conversionDefinition.InAmount));
                }
            }

            ProcessEventTrigger(player, trigger, resultingNotices);

            CheckTriggers(player, eventTriggers, resultingNotices);
        }
Beispiel #6
0
        /// <summary>
        /// Applies the requested animal assignment data, cooking animals
        /// for food in the process
        /// </summary>
        /// <param name="player"></param>
        /// <param name="data"></param>
        public static void AssignAnimals(AgricolaPlayer player, AnimalCacheActionData data, List <GameActionNotice> resultingNotices)
        {
            player.AssignAnimals(data.Assignments);

            var cooking = false;

            foreach (var count in data.Cook.Values)
            {
                if (count > 0)
                {
                    cooking = true;
                    break;
                }
            }

            var freedAnimalsPredicates = new List <INoticePredicate>();

            foreach (var animal in data.Free.Keys)
            {
                if (data.Free[animal] > 0)
                {
                    freedAnimalsPredicates.Add(new ResourceCache((Resource)animal, data.Free[animal]));
                }
            }
            if (freedAnimalsPredicates.Count > 0)
            {
                resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.FreeAnimals.ToString(), freedAnimalsPredicates));
            }


            if (cooking)
            {
                var conversions            = Curator.GetHarvestFoodValues(player);
                var cookedAnimalPredicates = new List <INoticePredicate>();
                foreach (var animal in data.Cook.Keys)
                {
                    if (data.Cook[animal] > 0)
                    {
                        var definition  = conversions.Where(x => x.InType.ToString() == animal.ToString()).OrderByDescending(x => x.OutAmount).First();
                        var inputCache  = new ResourceCache((Resource)animal, data.Cook[animal]);
                        var outputCache = new ResourceCache(Resource.Food, definition.OutAmount * data.Cook[animal]);
                        player.AddResource(outputCache);
                        cookedAnimalPredicates.Add(new ConversionPredicate(inputCache, outputCache));
                    }
                }
                if (cookedAnimalPredicates.Count > 0)
                {
                    resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.Converted.ToString(), cookedAnimalPredicates));
                }
            }
        }
Beispiel #7
0
        public override GameAction OnExecute(AgricolaPlayer player, Data.GameActionData data)
        {
            base.OnExecute(player, data);

            var choiceData = (AnimalChoiceActionData)data;

            if (choiceData.Option == AnimalResource.Sheep)
            {
                player.AddResource(Resource.Food);
            }
            else if (choiceData.Option == AnimalResource.Cattle)
            {
                player.RemoveResource(Resource.Food);
            }

            ActionService.AssignAnimals(player, choiceData.AnimalData, ResultingNotices);
            return(this);
        }
Beispiel #8
0
        /// <summary>
        /// Assigns a single resource to a player and triggers
        /// events.
        /// </summary>
        /// <param name="player"></param>
        /// <param name="cache"></param>
        /// <param name="eventTriggers">Triggers attached to the calling actions.</param>
        /// <param name="resultingNotices"></param>
        /// <param name="partOfMultiCache"></param>
        public static void AssignCacheResource(AgricolaPlayer player, ImmutableList <GameEventTrigger> eventTriggers, List <GameActionNotice> resultingNotices, ResourceCache cache, bool partOfMultiCache = false)
        {
            if (cache.Type.IsAnimal())
            {
                //player.Game.AddInterrupt(new AssignAnimalsAction(player, cache, resultingNotices));
            }
            else
            {
                player.AddResource(cache.Type, cache.Count);
                resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.Take.ToString(), new ResourceCache(cache.Type, cache.Count)));

                var resourceTrigger = new TakeCachedResourceTrigger(cache.Type);
                ProcessEventTrigger(player, resourceTrigger, resultingNotices);

                if (!partOfMultiCache)
                {
                    var onlyResourceTrigger = new TakeSoleCachedResourceTrigger(cache.Type);
                    ProcessEventTrigger(player, onlyResourceTrigger, resultingNotices);
                }

                CheckTriggers(player, eventTriggers, resultingNotices);
            }
        }
Beispiel #9
0
        public static void BuyImprovement(AgricolaPlayer player, ImprovementActionData data, List <GameActionNotice> resultingNotices)
        {
            var improvementData = (ImprovementActionData)data;
            var card            = ((AgricolaGame)player.Game).GetCard(improvementData.Id);
            var cost            = Curator.GetCardCost(player, improvementData.Id, improvementData.PaymentOption);

            if (cost is ResourceCardCost)
            {
                var rcCost = (ResourceCardCost)cost;
                foreach (var resource in rcCost.Resources)
                {
                    if (resource.Type.IsAnimal())
                    {
                        player.RemoveAnimals((AnimalResource)resource.Type, resource.Count);
                    }
                    else
                    {
                        player.AddResource(resource.Type, -resource.Count);
                    }
                }
            }
            else if (cost is ReturnCardCardCost)
            {
                var miCost       = (ReturnCardCardCost)cost;
                var ownedCardIds = player.OwnedCardIds;

                foreach (var id in miCost.Ids)
                {
                    if (ownedCardIds.Contains(id))
                    {
                        ((AgricolaGame)player.Game).ReturnCard(player, id);
                        break;
                    }
                }
            }
            else if (!(cost is FreeCardCost))
            {
                throw new NotImplementedException("Cost type not supported.");
            }

            // Apply the card
            if (card is MajorImprovement)
            {
                ((AgricolaGame)player.Game).AssignMajorImprovement(improvementData.Id, player);
            }
            else if (card is MinorImprovement)
            {
                if (((MinorImprovement)card).PassesLeft)
                {
                    ((AgricolaGame)player.Game).PassCardLeft(player, (MinorImprovement)card);
                }
                else
                {
                    player.PlayCard(card);
                }
            }

            resultingNotices.Add(new GameActionNotice(player.Name, NoticeVerb.PurchaseImprovement.ToString(), new IdPredicate(data.Id)));
            foreach (var evnt in card.OnPlayEvents)
            {
                evnt.Execute(player, null, card, resultingNotices);
            }
        }