示例#1
0
        protected override IInteraction Apply(HengeInteraction interaction)
        {
            //TODO: Need to check if the Actor is a logged-out Avatar and give them bonuses if so.
            if (this.Validate(interaction) && !interaction.Finished)
            {
                Actor actor			= interaction.Antagonist as Actor;
                Trait health		= actor.Traits["Health"];
                Trait energy		= actor.Traits["Energy"];
                Trait reserve		= actor.Traits["Reserve"];
                Trait constitution	= actor.Traits["Constitution"];
                string message		= "you rested and recuperated a little";
                double constDelta	= Constants.Tick.MetabolicRate;
                double healthDelta	= (health.Value < health.Maximum) ? Constants.Tick.Healthy.Heal : 0;
                double energyDelta	= (reserve.Value < reserve.Maximum) ? Constants.Tick.Healthy.Revitalise : 0;
                constDelta+= (healthDelta + energyDelta);

                if (constitution.Value <= 0)
                {
                    // Decrease Health, increase Energy by less
                    healthDelta	= Constants.Tick.Ill.Heal;
                    energyDelta	= Constants.Tick.Ill.Revitalise;
                    constDelta	= -constDelta;
                    message		= "you felt weaker";

                    // Increase Constitution
                    if (constitution.Value == 0) constDelta = 0;
                }

                if (health.Value + healthDelta < 0)
                {
                    using (interaction.Lock(health, reserve, energy, constitution, actor.Ticks))
                    {
                        //When the actor dies, all ticks should be cancelled
                        actor.Ticks.Clear();
                        health.SetValue(0);
                        energy.SetValue(0);
                        reserve.SetValue(0);
                        constitution.SetValue(constitution.Minimum);
                        health.Flavour = "Dead";
                    }
                    interaction.Success("you succumbed to your ailments. Your story is over... will your line continue?");
                }
                else
                {
                    using (interaction.Lock(health, reserve, constitution))
                    {
                        health.SetValue(health.Value + healthDelta);
                        reserve.SetValue(reserve.Value + energyDelta);
                        constitution.SetValue(constitution.Value - constDelta);
                    }
                    interaction.Success(message);
                }
            }
            return interaction;
        }
示例#2
0
        protected override IInteraction Apply(HengeInteraction interaction)
        {
            if (!interaction.Finished && this.Validate(interaction))
            {
                Item food			= interaction.Antagonist as Item;
                Actor actor 		= interaction.Protagonist as Actor;
                double nutrition	= food.Traits["Nutrition"].Value;

                if (nutrition > 0)
                {
                    interaction.Success(string.Format("You eat the {0} with relish", food.Inspect(actor)));
                }
                else
                {
                    if (nutrition == 0) interaction.Success(string.Format("You eat the {0}", food.Inspect(actor)));
                    else interaction.Success(string.Format("You eat the {0}. You feel queasy.", food.Inspect(actor)));
                }

                if (food.Owner == actor)
                {
                    Trait weight 		= actor.Traits["Weight"];
                    Trait constitution	= actor.Traits["Constitution"];

                    using (interaction.Lock(actor.Inventory, weight, constitution))
                    {
                        weight.SetValue(weight.Value - food.Traits["Weight"].Value);
                        constitution.SetValue(constitution.Value + nutrition);
                        actor.Inventory.Remove(food);
                    }
                    interaction.Delete(food);
                }
                else interaction.Failure("You no longer have that", true);

            }
            return interaction;
        }
示例#3
0
文件: Talk.cs 项目: justen/henge
        protected override IInteraction Apply(HengeInteraction interaction)
        {
            if (!interaction.Finished && this.Validate(interaction))
            {
                if (interaction.ProtagonistCache.UseEnergy(Constants.TalkCost, EnergyType.None))
                {
                    if (interaction.Arguments.ContainsKey("Message"))
                    {
                        List<Avatar> recipients	= interaction.Arguments["Recipients"] as List<Avatar>;
                        if (recipients==null) recipients = new List<Avatar>();

                        string target		= (recipients.Count > 1) ? "out loud" : "to you";
                        string message		= string.Format("{0} says \"{1}\" {2}.", interaction.Protagonist.Name, interaction.Arguments["Message"] as string, target);
                        DateTime occurred	= DateTime.Now;
                        foreach (Avatar recipient in recipients)
                        {
                            //Log the speech
                            using (interaction.Lock(recipient.Log))
                            {
                                // Possibly inefficient to lock each recipient's log individually. Also, shouldn't
                                // we be using the relational DB for this sort of thing?
                                recipient.Log.Add(new LogEntry(){ Entry = message, Occurred = occurred});
                            }
                        }
                        if (recipients.Count == 1)
                        {
                            target = string.Format("to {0}", recipients[0].Name);
                        }
                        interaction.Success(string.Format("You say \"{0}\" {0}.", interaction.Arguments["Message"], target));
                    }
                    else interaction.Failure("You have nothing to say", false);
                }
                else interaction.Failure("You are too tired even to speak", false);
            }
            return interaction;
        }
示例#4
0
        protected void ApplyInteraction(HengeInteraction interaction, Actor actor, Location target)
        {
            int dx					= actor.Location.X - target.X;
            int dy 					= actor.Location.Y - target.Y;
            char [] inDirection		= new char [] {
                (dx > 0) ? 'e' : (dx < 0) ? 'w' : '-',
                (dy > 0) ? 's' : (dy < 0) ? 'n' : '-'
            };

            char [] outDirection		= new char [] {
                (dx < 0) ? 'e' : (dx > 0) ? 'w' : '-',
                (dy < 0) ? 's' : (dy > 0) ? 'n' : '-'
            };
            double baseTrack =  actor.Traits.ContainsKey("Tracks")? actor.Traits["Tracks"].Value : Constants.BaseTrack;
            double trackOut = baseTrack * (actor.Location.Traits.ContainsKey("Tracks")?actor.Location.Traits["Tracks"].Value : 0);
            double trackIn = baseTrack * (target.Traits.ContainsKey("Tracks")?target.Traits["Tracks"].Value : 0);

            if (actor is Avatar)
            {
                Dictionary<string, int> timesIn = new Dictionary<string, int>();
                Dictionary<string, int> timesOut = new Dictionary<string, int>();
                foreach(Trait track in target.TracesOut)
                {
                    if (DateTime.Now<(DateTime)(track.Expiry))
                    {
                        Actor person = track.Subject as Actor;
                        if (timesOut.ContainsKey(person.Name))
                        {
                            timesOut[person.Name]++;
                        }
                        else timesOut.Add(person.Name, 1);
                    }
                }
                foreach(Trait track in target.TracesIn)
                {
                    if(DateTime.Now<(DateTime)(track.Expiry))
                    {
                        Actor person = track.Subject as Actor;
                        if (timesIn.ContainsKey(person.Name))
                        {
                            timesIn[person.Name]++;
                        }
                        else timesIn.Add(person.Name, 1);
                    }
                }
                bool beenHere = false;
                foreach(string name in timesIn.Keys)
                {
                    if (name!=actor.Name)
                    {
                        int outTimes = timesOut.ContainsKey(name)?timesOut[name] : 0;
                        int totalTraffic = timesIn[name] + outTimes;
                        if (totalTraffic <3)
                        {
                            interaction.Log += (name + " has been here. ");
                        }
                        else
                        {
                            if (totalTraffic < 6)
                            {
                                interaction.Log += (name + " has been here more than once. ");
                            }
                            else
                            {
                                interaction.Log += (name + " has been here frequently. ");
                            }
                        }
                        if (outTimes < timesIn[name]) interaction.Log += "You cannot see any of their tracks leading away. ";
                    }
                    else beenHere = true;
                }
                if (timesOut.ContainsKey(actor.Name))
                {
                    beenHere = true;
                }
                if (beenHere) interaction.Log += " It looks like you've been here before. ";
                Avatar avatar = actor as Avatar;
                                //potential bottleneck here - may want to do smarter locking
                using (interaction.Lock(avatar, avatar.Location.Inhabitants, target.Inhabitants, avatar.Location.TracesOut, target.TracesIn))
                {
                    this.AddTracks(avatar.Location, avatar, false, outDirection.ToString(), trackOut, interaction);
                    this.AddTracks(target, avatar, true, inDirection.ToString(), trackIn, interaction);
                    avatar.Location.Inhabitants.Remove(avatar);
                    target.Inhabitants.Add(avatar);
                    avatar.Location = target;

                }
                interaction.Success(string.Format("You reach your destination, a {0}", target.Inspect(avatar).ShortDescription));
            }
            else
            {
                Npc npc = actor as Npc;

                using (interaction.Lock(npc, npc.Location.Fauna, target.Fauna, npc.Location.TracesOut, target.TracesIn))
                {
                    this.AddTracks(npc.Location, npc, false, outDirection.ToString(), trackOut, interaction);
                    this.AddTracks(target, npc, true, inDirection.ToString(), trackIn, interaction);
                    npc.Location.Fauna.Remove(npc);
                    target.Fauna.Add(npc);
                    npc.Location = target;
                }

                interaction.Success("Moved");
            }
        }
示例#5
0
        protected override IInteraction Apply(HengeInteraction interaction)
        {
            if (this.Validate(interaction) )
            {
                if ( interaction.ProtagonistCache.Energy > 0)
                {
                    Actor protagonist	= interaction.Protagonist as Actor;
                    Location source		= protagonist.Location;
                    Location target		= interaction.Antagonist as Location;

                    if (target.Map == source.Map)
                    {
                        if (source.CanSee(target))
                        {
                            double dx			= target.X - source.X;
                            double dy			= target.Y - source.Y;
                            double distance		= dx * dx + dy * dy;
                            double sourceCover	= source.Traits.ContainsKey("Cover") ? source.Traits["Cover"].Value : Constants.DefaultCover;
                            double targetCover	= target.Traits.ContainsKey("Cover") ? target.Traits["Cover"].Value : Constants.DefaultCover;
                            distance			= distance * Math.Max(sourceCover, targetCover);
                            double detection	= protagonist.Skills["Perception"].Value;
                            double difficulty	= distance * Constants.EdificeScouting;
                            int success = 0;
                            bool weary = false;

                            switch (interaction.ProtagonistCache.SkillCheck("Perception", distance * Constants.LocationScouting, Constants.ScoutCost, Constants.ScoutCost, EnergyType.Concentration))
                            {
                            case SkillResult.PassSufficient:
                                    interaction.Results.Add("Location", target);
                                    success=1;
                                    break;
                            case SkillResult.FailSufficient: break;
                            default: weary = true; break;
                            }
                            switch (interaction.ProtagonistCache.SkillCheck("Perception", difficulty, Constants.ScoutCost, Constants.ScoutCost, EnergyType.Concentration))
                            {
                            case SkillResult.PassSufficient:
                                    success++;
                                    interaction.Results.Add("Structures", target.Structures.Where(c => c.Traits.ContainsKey("Visibility") && c.Traits["Visibility"].Value >= detection - difficulty).ToList());
                                    difficulty = distance * Constants.ActorScouting;
                                    break;
                            case SkillResult.FailSufficient: break;
                            default: weary = true; break;
                            }
                            switch (interaction.ProtagonistCache.SkillCheck("Perception", difficulty, Constants.ScoutCost, Constants.ScoutCost, EnergyType.Concentration))
                            {
                            case SkillResult.PassSufficient:
                                        difficulty = detection - difficulty;
                                        interaction.Results.Add("NPCs", target.Fauna.Where(c => c.Traits.ContainsKey("Visibility") && c.Traits["Visibility"].Value >= difficulty).ToList());
                                        interaction.Results.Add("Avatars", target.Inhabitants.Where(c => c.Traits.ContainsKey("Visibility") && c.Traits["Visibility"].Value >= difficulty).ToList());
                                        success ++;
                                        break;
                            case SkillResult.FailSufficient: break;
                            default: weary = true; break;
                            }
                            if (weary) interaction.Log+="Your tired eyes may not be trustworthy, but you";
                            else interaction.Log+= "You ";
                            switch (success)
                            {
                            case 3: interaction.Success("feel that you have a good view of the area");
                                    break;
                            case 2: interaction.Success("can see the area reasonably well");
                                    break;
                            case 1: interaction.Success("can just about make out the terrain");
                                    break;
                            default: interaction.Failure("can't make anything out", false); break;
                            }
                        }
                        else interaction.Failure("You can't see from here", false);
                    }
             		else interaction.Failure("You are attempting to scout a location you cannot see", true);
                } else interaction.Failure("You are too tired to focus on scouting", false);
            }
            return interaction;
        }
示例#6
0
        protected override IInteraction Apply(HengeInteraction interaction)
        {
            if (!interaction.Finished && this.Validate(interaction))
            {
                Actor protagonist		= interaction.Protagonist as Actor;
                Component antagonist	= interaction.Antagonist;

                //Hiding a Location is dumb, and will just fail.
                if (antagonist is Location)
                {
                    interaction.Failure("You cannot hide a location", true);
                }
                else
                {
                    //You can try to hide pretty much anything else.
                    //I suspect hiding a building is going to be a bit very impossible,
                    //but we can handle that by simply giving Edifices very, very large Conspicuousness values.
                    //Difficulty of hiding something depends upon
                    // 1) Conspicuousness of the thing being hidden
                    // 2) Things interfering
                    // - Up to this point, the running total is cached in interaction.Impedance -
                    // 3) The "Cover" trait of the Location - even if you're useless at hiding stuff, this could make it easier
                    // 4) The protagonists "Hide" skill

                    double visibility = Constants.StandardVisibility;

                    //This is going to cost us Some Energy. The better we hid it, the more effort it took, so...
                    double maxEnergy	= interaction.Protagonist.Traits["Energy"].Maximum;
                    double best			= interaction.ProtagonistCache.Energy / maxEnergy;
                    double randomNumber	= Constants.RandomNumber;
                    randomNumber		= (randomNumber > best) ? best : randomNumber;

                    if (randomNumber > 0)
                    {

                        //So, the worst-case visibility is now known.
                        //difficulty is in Impedance, need to modify it by the cover available:
                        switch (interaction.ProtagonistCache.SkillCheck("Hide", interaction.Impedance / protagonist.Location.Traits["Cover"].Value, randomNumber * maxEnergy, randomNumber * maxEnergy, EnergyType.Concentration))
                        {
                        case SkillResult.PassSufficient:
                            //You've hidden it. But how well?
                            //Let's add our rng result to the hide skill and divide by two
                            visibility -= visibility * (interaction.Protagonist.Skills.ContainsKey("Hide") ? 0.5 * (randomNumber + interaction.Protagonist.Skills["Hide"].Value) : 0.5 * randomNumber);

                            if (antagonist is Avatar)	interaction.Success(string.Format("You attempt to conceal {0}", antagonist.Name));
                            else 						interaction.Success(string.Format("You attempt to conceal the {0}", antagonist.Inspect(protagonist).ShortDescription));
                            break;

                        case SkillResult.PassExhausted:
                            interaction.Failure("You are too tired", false);
                            break;

                        default: interaction.Failure("Your skill at concealing things isn't up to the task", false);
                            break;
                        }
                        visibility *= interaction.AntagonistCache.Conspicuousness;
                        if (antagonist is Item && (antagonist as Item).Owner == protagonist)
                        {
                            Item item 				= antagonist as Item;
                            Trait protagonistWeight = protagonist.Traits["Weight"];

                            using (interaction.Lock(protagonist.Location.Inventory, item, protagonistWeight, protagonist.Inventory))
                            {
                                protagonist.Location.Inventory.Add(item);
                                item.Owner = protagonist.Location;
                                protagonist.Traits["Weight"].SetValue(protagonist.Traits["Weight"].Value - item.Traits["Weight"].Value);
                                protagonist.Inventory.Remove(item);
                            }
                        }
                        using (interaction.Lock(antagonist.Traits))
                        {
                            if (antagonist.Traits.ContainsKey("Visibility"))
                            {
                                // Not sure how safe it is to use recursive locking?
                                using (interaction.Lock(antagonist.Traits["Visibility"]))
                                {
                                    antagonist.Traits["Visibility"].SetValue(visibility);
                                }
                            }
                            else antagonist.Traits.Add("Visibility", new Trait(double.MaxValue, 0, visibility));

                        }
                    }
                    else
                    {
                        interaction.Failure("You can see nowhere to hide that", false);
                    }
                }
            }
            return interaction;
        }