- .streamsclear re-added. It will remove all followed streams on the server.

- .gifts now have 3 new ✂️ Haircut 🧻 ToiletPaper and 🥀 WiltedRose which **reduce** waifu's value
- Added a new multiplier (waifu.multi.negative_gift_effect default 0.5, changeable via .config gambling or data/gambling.yml)
This commit is contained in:
Kwoth
2021-09-30 08:53:15 +02:00
parent 52c9ec670d
commit ff95b3d00f
12 changed files with 247 additions and 159 deletions

View File

@@ -4,6 +4,15 @@ Experimental changelog. Mostly based on [keepachangelog](https://keepachangelog.
## Unreleased ## Unreleased
### Added
- `.streamsclear` re-added. It will remove all followed streams on the server.
- `.gifts` now have 3 new ✂️ Haircut 🧻 ToiletPaper and 🥀 WiltedRose which **reduce** waifu's value
- They are called negative gifts
- They show up at the end of the `.gifts` page and are marked with a broken heart
- They have a separate multiplier (`waifu.multi.negative_gift_effect` default 0.5, changeable via `.config gambling` or `data/gambling.yml`)
- When gifted, the waifu's price will be reduced by the `price * multiplier`
- Negative gifts don't show up in `.waifuinfo` nor is the record of them kept in the database
## [3.0.6] - 27.09.2021 ## [3.0.6] - 27.09.2021
### Added ### Added

View File

@@ -3,6 +3,7 @@ using System.Collections.Generic;
using Cloneable; using Cloneable;
using NadekoBot.Common; using NadekoBot.Common;
using NadekoBot.Common.Yml; using NadekoBot.Common.Yml;
using YamlDotNet.Serialization;
namespace NadekoBot.Modules.Gambling.Common namespace NadekoBot.Modules.Gambling.Common
{ {
@@ -179,7 +180,8 @@ default is 0.02, which is 2%")]
public MultipliersData Multipliers { get; set; } = new MultipliersData(); public MultipliersData Multipliers { get; set; } = new MultipliersData();
[Comment(@"List of items available for gifting.")] [Comment(@"List of items available for gifting.
If negative is true, gift will instead reduce waifu value.")]
public List<WaifuItemModel> Items { get; set; } = new List<WaifuItemModel>(); public List<WaifuItemModel> Items { get; set; } = new List<WaifuItemModel>();
public WaifuConfig() public WaifuConfig()
@@ -260,6 +262,11 @@ Default 1 (meaning no effect)")]
Default 0.95 (meaning 95%) Default 0.95 (meaning 95%)
Example: If a waifu is worth 1000, and she receives a gift worth 100, her new value will be 1095)")] Example: If a waifu is worth 1000, and she receives a gift worth 100, her new value will be 1095)")]
public decimal GiftEffect { get; set; } = 0.95M; public decimal GiftEffect { get; set; } = 0.95M;
[Comment(@"What percentage of the value of the gift will a waifu lose when she's gifted a gift marked as 'negative'.
Default 0.5 (meaning 50%)
Example: If a waifu is worth 1000, and she receives a negative gift worth 100, her new value will be 950)")]
public decimal NegativeGiftEffect { get; set; } = 0.50M;
} }
[Cloneable] [Cloneable]
@@ -269,18 +276,23 @@ Example: If a waifu is worth 1000, and she receives a gift worth 100, her new va
public int Price { get; set; } public int Price { get; set; }
public string Name { get; set; } public string Name { get; set; }
[YamlMember(DefaultValuesHandling = DefaultValuesHandling.OmitDefaults)]
public bool Negative { get; set; }
public WaifuItemModel() public WaifuItemModel()
{ {
} }
public WaifuItemModel(string itemEmoji, int price, string name) public WaifuItemModel(string itemEmoji, int price, string name, bool negative = false)
{ {
ItemEmoji = itemEmoji; ItemEmoji = itemEmoji;
Price = price; Price = price;
Name = name; Name = name;
Negative = negative;
} }
public override string ToString() => Name; public override string ToString() => Name;
} }

View File

@@ -1,7 +1,11 @@
using NadekoBot.Common; using System;
using System.Collections.Generic;
using System.Linq;
using NadekoBot.Common;
using NadekoBot.Common.Configs; using NadekoBot.Common.Configs;
using NadekoBot.Modules.Gambling.Common; using NadekoBot.Modules.Gambling.Common;
using NadekoBot.Services; using NadekoBot.Services;
using NadekoBot.Services.Database.Models;
namespace NadekoBot.Modules.Gambling.Services namespace NadekoBot.Modules.Gambling.Services
{ {
@@ -34,9 +38,31 @@ namespace NadekoBot.Modules.Gambling.Services
AddParsedProp("waifu.multi.divorce_value", gs => gs.Waifu.Multipliers.DivorceNewValue, decimal.TryParse, ConfigPrinters.ToString, val => val > 0); AddParsedProp("waifu.multi.divorce_value", gs => gs.Waifu.Multipliers.DivorceNewValue, decimal.TryParse, ConfigPrinters.ToString, val => val > 0);
AddParsedProp("waifu.multi.all_gifts", gs => gs.Waifu.Multipliers.AllGiftPrices, decimal.TryParse, ConfigPrinters.ToString, val => val > 0); AddParsedProp("waifu.multi.all_gifts", gs => gs.Waifu.Multipliers.AllGiftPrices, decimal.TryParse, ConfigPrinters.ToString, val => val > 0);
AddParsedProp("waifu.multi.gift_effect", gs => gs.Waifu.Multipliers.GiftEffect, decimal.TryParse, ConfigPrinters.ToString, val => val >= 0); AddParsedProp("waifu.multi.gift_effect", gs => gs.Waifu.Multipliers.GiftEffect, decimal.TryParse, ConfigPrinters.ToString, val => val >= 0);
AddParsedProp("waifu.multi.negative_gift_effect", gs => gs.Waifu.Multipliers.NegativeGiftEffect, decimal.TryParse, ConfigPrinters.ToString, val => val >= 0);
AddParsedProp("decay.percent", gs => gs.Decay.Percent, decimal.TryParse, ConfigPrinters.ToString, val => val >= 0 && val <= 1); AddParsedProp("decay.percent", gs => gs.Decay.Percent, decimal.TryParse, ConfigPrinters.ToString, val => val >= 0 && val <= 1);
AddParsedProp("decay.maxdecay", gs => gs.Decay.MaxDecay, int.TryParse, ConfigPrinters.ToString, val => val >= 0); AddParsedProp("decay.maxdecay", gs => gs.Decay.MaxDecay, int.TryParse, ConfigPrinters.ToString, val => val >= 0);
AddParsedProp("decay.threshold", gs => gs.Decay.MinThreshold, int.TryParse, ConfigPrinters.ToString, val => val >= 0); AddParsedProp("decay.threshold", gs => gs.Decay.MinThreshold, int.TryParse, ConfigPrinters.ToString, val => val >= 0);
Migrate();
}
private readonly IEnumerable<WaifuItemModel> antiGiftSeed = new[]
{
new WaifuItemModel("🥀", 100, "WiltedRose", true),
new WaifuItemModel("✂️", 1000, "Haircut", true),
new WaifuItemModel("🧻", 10000, "ToiletPaper", true),
};
public void Migrate()
{
if (_data.Version < 2)
{
ModifyConfig(c =>
{
c.Waifu.Items = c.Waifu.Items.Concat(antiGiftSeed).ToList();
c.Version = 2;
});
}
} }
} }
} }

View File

@@ -394,6 +394,8 @@ namespace NadekoBot.Modules.Gambling.Services
}); });
} }
if (!itemObj.Negative)
{
w.Items.Add(new WaifuItem() w.Items.Add(new WaifuItem()
{ {
Name = itemObj.Name.ToLowerInvariant(), Name = itemObj.Name.ToLowerInvariant(),
@@ -402,12 +404,19 @@ namespace NadekoBot.Modules.Gambling.Services
if (w.Claimer?.UserId == from.Id) if (w.Claimer?.UserId == from.Id)
{ {
w.Price += (int) (itemObj.Price * _gss.Data.Waifu.Multipliers.GiftEffect); w.Price += (int)(itemObj.Price * _gss.Data.Waifu.Multipliers.GiftEffect);
} }
else else
{ {
w.Price += itemObj.Price / 2; w.Price += itemObj.Price / 2;
} }
}
else
{
w.Price -= (int)(itemObj.Price * _gss.Data.Waifu.Multipliers.NegativeGiftEffect);
if (w.Price < 1)
w.Price = 1;
}
await uow.SaveChangesAsync(); await uow.SaveChangesAsync();
} }
@@ -512,7 +521,7 @@ namespace NadekoBot.Modules.Gambling.Services
{ {
var conf = _gss.Data; var conf = _gss.Data;
return conf.Waifu.Items return conf.Waifu.Items
.Select(x => new WaifuItemModel(x.ItemEmoji, (int)(x.Price * conf.Waifu.Multipliers.AllGiftPrices), x.Name)) .Select(x => new WaifuItemModel(x.ItemEmoji, (int)(x.Price * conf.Waifu.Multipliers.AllGiftPrices), x.Name, x.Negative))
.ToList(); .ToList();
} }
} }

View File

@@ -317,10 +317,14 @@ namespace NadekoBot.Modules.Gambling
.WithOkColor(); .WithOkColor();
waifuItems waifuItems
.OrderBy(x => x.Price) .OrderBy(x => x.Negative)
.ThenBy(x => x.Price)
.Skip(9 * cur) .Skip(9 * cur)
.Take(9) .Take(9)
.ForEach(x => embed.AddField($"{x.ItemEmoji} {x.Name}", x.Price, true)); .ForEach(x => embed
.AddField($"{(!x.Negative ? string.Empty : "\\💔")} {x.ItemEmoji} {x.Name}",
Format.Bold(x.Price.ToString()) + _config.Currency.Sign,
true));
return embed; return embed;
}, waifuItems.Count, 9); }, waifuItems.Count, 9);

View File

@@ -73,7 +73,6 @@ namespace NadekoBot.Modules.Games.Hangman
return new(output); return new(output);
} }
// todo lock
public State Guess(string guess) public State Guess(string guess)
{ {
if (CurrentPhase != Phase.Running) if (CurrentPhase != Phase.Running)

View File

@@ -14,6 +14,8 @@ using NadekoBot.Extensions;
using StackExchange.Redis; using StackExchange.Redis;
using Discord; using Discord;
using Discord.WebSocket; using Discord.WebSocket;
using LinqToDB;
using LinqToDB.EntityFrameworkCore;
using NadekoBot.Common.Collections; using NadekoBot.Common.Collections;
using NadekoBot.Common.Replacements; using NadekoBot.Common.Replacements;
using NadekoBot.Db; using NadekoBot.Db;
@@ -342,19 +344,18 @@ namespace NadekoBot.Modules.Searches.Services
return Task.CompletedTask; return Task.CompletedTask;
} }
public int ClearAllStreams(ulong guildId) public async Task<int> ClearAllStreams(ulong guildId)
{
// todo future clear streams
int count;
using (var uow = _db.GetDbContext())
{ {
using var uow = _db.GetDbContext();
var gc = uow.GuildConfigsForId(guildId, set => set.Include(x => x.FollowedStreams)); var gc = uow.GuildConfigsForId(guildId, set => set.Include(x => x.FollowedStreams));
count = gc.FollowedStreams.Count; uow.RemoveRange(gc.FollowedStreams);
gc.FollowedStreams.Clear();
uow.SaveChanges();
}
return count; foreach (var s in gc.FollowedStreams)
await PublishUnfollowStream(s);
uow.SaveChanges();
return gc.FollowedStreams.Count;
} }
public async Task<FollowedStream> UnfollowStreamAsync(ulong guildId, int index) public async Task<FollowedStream> UnfollowStreamAsync(ulong guildId, int index)

View File

@@ -69,14 +69,14 @@ namespace NadekoBot.Modules.Searches
fs.Type)); fs.Type));
} }
// [NadekoCommand, Usage, Description, Aliases] [NadekoCommand, Usage, Description, Aliases]
// [RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]
// [UserPerm(GuildPerm.Administrator)] [UserPerm(GuildPerm.Administrator)]
// public async Task StreamsClear() public async Task StreamsClear()
// { {
// var count = _service.ClearAllStreams(ctx.Guild.Id); var count = _service.ClearAllStreams(ctx.Guild.Id);
// await ReplyErrorLocalizedAsync(strs.streams_cleared(count))); await ReplyConfirmLocalizedAsync(strs.streams_cleared);
// } }
[NadekoCommand, Aliases] [NadekoCommand, Aliases]
[RequireContext(ContextType.Guild)] [RequireContext(ContextType.Guild)]

View File

@@ -532,6 +532,9 @@ streamadd:
streamremove: streamremove:
- streamremove - streamremove
- strm - strm
streamsclear:
- streamsclear
- stclear
streamlist: streamlist:
- streamlist - streamlist
- stl - stl

View File

@@ -1,5 +1,5 @@
# DO NOT CHANGE # DO NOT CHANGE
version: 1 version: 2
# Currency settings # Currency settings
currency: currency:
# What is the emoji/character which represents the currency # What is the emoji/character which represents the currency
@@ -107,7 +107,12 @@ waifu:
# Default 0.95 (meaning 95%) # Default 0.95 (meaning 95%)
# Example: If a waifu is worth 1000, and she receives a gift worth 100, her new value will be 1095) # Example: If a waifu is worth 1000, and she receives a gift worth 100, her new value will be 1095)
giftEffect: 0.95 giftEffect: 0.95
# What percentage of the value of the gift will a waifu lose when she's gifted a gift marked as 'negative'.
# Default 0.5 (meaning 50%)
# Example: If a waifu is worth 1000, and she receives a negative gift worth 100, her new value will be 950)
negativeGiftEffect: 0.50
# List of items available for gifting. # List of items available for gifting.
# If negative is true, gift will instead reduce waifu value.
items: items:
- itemEmoji: "🥔" - itemEmoji: "🥔"
price: 5 price: 5
@@ -217,6 +222,18 @@ waifu:
- itemEmoji: "🌕" - itemEmoji: "🌕"
price: 50000 price: 50000
name: Moon name: Moon
- itemEmoji: "🥀"
price: 100
name: WiltedRose
negative: true
- itemEmoji: ✂️
price: 1000
name: Haircut
negative: true
- itemEmoji: "🧻"
price: 10000
name: ToiletPaper
negative: true
# Amount of currency selfhosters will get PER pledged dollar CENT. # Amount of currency selfhosters will get PER pledged dollar CENT.
# 1 = 100 currency per $. Used almost exclusively on public nadeko. # 1 = 100 currency per $. Used almost exclusively on public nadeko.
patreonCurrencyPerCent: 1 patreonCurrencyPerCent: 1

View File

@@ -902,6 +902,10 @@ streamadd:
desc: "Notifies this channel when the stream on the specified URL goes online or offline. Offline notifications will only show if you enable `{0}streamoff`. Maximum 10 per server." desc: "Notifies this channel when the stream on the specified URL goes online or offline. Offline notifications will only show if you enable `{0}streamoff`. Maximum 10 per server."
args: args:
- "twitch.tv/someguy" - "twitch.tv/someguy"
streamsclear:
desc: "Removes all followed streams on this server."
args:
- ""
streamremove: streamremove:
desc: "Stops following the stream on the specified index. (use `{0}stl` to see indexes)" desc: "Stops following the stream on the specified index. (use `{0}stl` to see indexes)"
args: args:
@@ -1433,7 +1437,10 @@ waifutransfer:
args: args:
- "@ExWaifu @NewOwner" - "@ExWaifu @NewOwner"
waifugift: waifugift:
desc: "Gift an item to someone. This will increase their waifu value by 50% of the gifted item's value if they are not your waifu, or 95% if they are. Provide no parameters to see a list of items that you can gift." desc: -|
Gift an item to someone. This will increase their waifu value by a percentage of the gift's value.
Negative gifts will not show up in waifuinfo.
Provide no parameters to see a list of items that you can gift.
args: args:
- "" - ""
- "Rose @Himesama" - "Rose @Himesama"

View File

@@ -507,6 +507,7 @@
"streamer_online": "Streamer {0} is online with {1} viewers.", "streamer_online": "Streamer {0} is online with {1} viewers.",
"streams_follow_title": "Streams you're following", "streams_follow_title": "Streams you're following",
"streams_none": "You are not following any streams on this server.", "streams_none": "You are not following any streams on this server.",
"streams_cleared": "All streams followed on this server have been removed.",
"stream_no": "No such stream.", "stream_no": "No such stream.",
"stream_off_enabled": "Stream notifications will now show when a stream goes offline.", "stream_off_enabled": "Stream notifications will now show when a stream goes offline.",
"stream_off_disabled": "Stream notifications will no longer show when a stream goes offline.", "stream_off_disabled": "Stream notifications will no longer show when a stream goes offline.",