public async Task <CurrentTask> SimulateTask(IDiscordBot bot, ApplicationUser user, SocketMessage message, SkillOption option) { var skill = Skill.IsSkill(option.SkillName); var skillId = Skill.GetId(option.SkillName); if (!skill) { await message.Channel.SendMessageAsync($"{message.Author.Mention} skill not found. Available skills {Skill.GetNames()}"); return(null); } option.SkillName = Skill.GetName(skillId); var emote = bot.GetEmote(option.SkillName); var skillTask = option.Task; var skillData = GetForName(skillTask, option.SkillName); if (skillData == null) { var allSkillItems = string.Join(", ", SkillingData.Where(t => t.Skill.Equals(option.SkillName, StringComparison.InvariantCultureIgnoreCase)).Select(t => t.Name)); await message.Channel.SendMessageAsync($"{message.Author.Mention} Invalid {emote} {option.SkillName} item name {skillTask}. All {option.SkillName} items: {allSkillItems}"); return(null); } var scaledTime = TimeSpan.FromMilliseconds(skillData.TimeTakenMillis * (1 + (100 - user.SkillSet.GetLevel(skillId)) / 100)); if (user.SkillSet.GetLevel(skillId) < skillData.Level) { await message.Channel.SendMessageAsync($"{message.Author.Mention} needs level {skillData.Level} {skillData.Skill} to {skillData.Action.ToLower()} {skillData.Name}. {emote}"); return(null); } if (!option.Amount.HasValue || option.Amount <= 0) { option.Amount = (int)Math.Floor(MaxTripLength.Divide(scaledTime)); } var duration = scaledTime.Multiply(option.Amount.Value); if (duration > MaxTripLength) { duration = MaxTripLength; option.Amount = (int)Math.Floor(MaxTripLength.TotalMilliseconds / scaledTime.TotalMilliseconds); } var end = DateTime.Now.Add(duration); var elapsed = end.Subtract(DateTime.Now); var requiredItems = skillData.ItemsRequired == null ? string.Empty : string.Join(", ", skillData.ItemsRequired.Where(item => !user.Bank.Contains(item.Item.ItemId) || user.Bank.GetAmount(item.Item.ItemId) < (item.Delete ? (ulong)option.Amount : 1)) .Select(item => $"{item.Item.Amount * (item.Delete ? (ulong)option.Amount : 1)} x {ItemDefinition.GetItemName(item.Item.ItemId)}")); if (!string.IsNullOrEmpty(requiredItems)) { await message.Channel.SendMessageAsync($"{message.Author.Mention} needs {requiredItems} to {skillData.Action.ToLower()} {skillData.Name}. {emote}"); return(null); } if (skillData.ItemsRequired != null && skillData.ItemsRequired.Any()) { skillData.ItemsRequired.Where(t => t.Delete) .ToList() .ForEach(item => { user.Bank.RemoveItem(new Item(item.Item.ItemId, (ulong)option.Amount)); user.Bank.UpdateRequired = true; }); } var taskDesc = $"{user.Mention} begins to {emote} {skillData.Action.ToLower()} {option.Amount} x {skillData.Name} for {elapsed.Hours}h {elapsed.Minutes}m {elapsed.Seconds}s!"; await message.Channel.SendMessageAsync(taskDesc); var task = new CurrentTask { ChannelId = message.Channel.Id, UnlockTime = end, TaskName = $"{emote} {option.SkillName} {option.Amount} x {skillData.Name}", MessageId = message.Id, ExpGains = new List <ExpGain>() { new ExpGain { Skill = skillId, Amount = option.Amount.Value * skillData.Xp } }, Items = skillData.ItemsGained?.Select(t => new TaskItem { Item = new Item { ItemId = t.ItemId, Amount = t.Amount * (ulong)option.Amount } }).ToList(), CompletionMessage = $"{user.Mention} has finished the task and retrieved {{1}}, you also received: \n {{0}}" }; var retriveStr = "nothing"; if (task.Items != null && task.Items.Any()) { retriveStr = string.Join(", ", task.Items.Select(v => $"{v.Item.Amount} x {ItemDefinition.GetItemName(v.Item.ItemId)}")); } task.CompletionMessage = task.CompletionMessage.Replace("{1}", retriveStr); return(task); }
public async Task <Stream> GetWidgetAsync(ShopWidgetOptions lootWidgetOptions) { var headerStream = ResourceExtensions.GetStreamCopy(typeof(Program), "RS3Bot.Cli.Images.Shop_Header.png"); using (var headerImage = Image.FromStream(headerStream)) using (var footerStream = ResourceExtensions.GetStreamCopy(typeof(Program), "RS3Bot.Cli.Images.Shop_Footer.png")) using (var footerImage = Image.FromStream(footerStream)) { var rowAmount = (int)Math.Ceiling(lootWidgetOptions.Items.Count / (double)MaxRowSize); var headerHeight = headerImage.Height; using (var lootImage = new Bitmap(headerImage.Width, headerHeight + (rowAmount * YSpacing) + FooterHeight)) using (var font = new Font(_fontCollection.Families[0], 8)) using (var shopItem = ResourceExtensions.GetStreamCopy(typeof(Program), "RS3Bot.Cli.Images.Shop_Item.png")) using (var rowStream = ResourceExtensions.GetStreamCopy(typeof(Program), "RS3Bot.Cli.Images.Shop_Row.png")) using (var rowImage = Image.FromStream(rowStream)) using (var shopItemImage = Image.FromStream(shopItem)) using (var titleFont = new Font(_fontCollection.Families[0], 40)) using (Graphics g = Graphics.FromImage(lootImage)) { g.DrawImage(headerImage, 0, 0); g.DrawString(lootWidgetOptions.Title, font, Brushes.Gold, 26, 12); for (int i = 0; i < lootWidgetOptions.Items.Count; i++) { var row = (int)Math.Floor(i / (double)MaxRowSize); var addNewRow = i % MaxRowSize == 0; var itemX = 30 + ((i % MaxRowSize) * XSpacing); var itemY = 80 + (row * YSpacing); var item = lootWidgetOptions.Items[i]; if (addNewRow) { g.DrawImage(rowImage, 0, headerHeight + (row * YSpacing)); } using (var itemStream = await _imageGrabber.GetAsync(item.Item.ItemId)) using (var imageStream = Image.FromStream(itemStream)) using (SolidBrush drawBrush = new SolidBrush(StackFormatter.GetColor(item.Item.Amount))) { var itemName = ItemDefinition.GetItemName(item.Item.ItemId); var itemNameLines = Split(itemName, MaxItemChar); var horizontalCenter = itemY + ((32 - imageStream.Height) / 2); var verticalCenter = itemX + ((32 - imageStream.Width) / 2); g.DrawImage(shopItemImage, itemX - 20, itemY - 15); g.DrawImage(imageStream, verticalCenter, horizontalCenter, imageStream.Width, imageStream.Height); g.DrawString(StackFormatter.QuantityToRSStackSize((long)item.Item.Amount), font, drawBrush, itemX - 7, itemY - 4); g.DrawString(itemName, font, Brushes.White, new RectangleF(new PointF(itemX + 34f, itemY - 0f), new SizeF(95, 36))); var amountStr = StackFormatter.QuantityToRSStackSize(item.Price); var amountMeasure = g.MeasureString(amountStr, font); g.DrawString(amountStr, font, Brushes.White, itemX + 113 - (amountMeasure.Width / 2), itemY + 26); } } g.DrawImage(footerImage, 0, lootImage.Height - FooterHeight); headerStream.Position = 0; lootImage.Save(headerStream, System.Drawing.Imaging.ImageFormat.Png); headerStream.Position = 0; } return(headerStream); } }