Skip to content

Commit

Permalink
Drake meme generator (#69)
Browse files Browse the repository at this point in the history
Co-authored-by: JatoMixo <[email protected]>
  • Loading branch information
conaticus and JatoMixo authored Jul 9, 2024
1 parent 3471b60 commit 9d2e262
Show file tree
Hide file tree
Showing 5 changed files with 192 additions and 126 deletions.
74 changes: 38 additions & 36 deletions Boolean/Boolean.csproj
Original file line number Diff line number Diff line change
@@ -1,36 +1,38 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net8.0</TargetFramework>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<UserSecretsId>4043f2b4-1120-4946-b098-003bba4cbbe4</UserSecretsId>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Discord.Net" Version="3.14.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="9.0.0-preview.3.24172.4" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="9.0.0-preview.3.24172.4">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="9.0.0-preview.3.24172.4">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.Extensions.Configuration" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.Hosting" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="9.0.0-preview.3" />
</ItemGroup>

<ItemGroup>
<None Update="appsettings.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
</ItemGroup>

</Project>
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net8.0</TargetFramework>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
<UserSecretsId>4043f2b4-1120-4946-b098-003bba4cbbe4</UserSecretsId>
</PropertyGroup>

<ItemGroup>
<PackageReference Include="Discord.Net" Version="3.14.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="9.0.0-preview.3.24172.4" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="9.0.0-preview.3.24172.4">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="9.0.0-preview.3.24172.4">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.Extensions.Configuration" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Microsoft.Extensions.Hosting" Version="9.0.0-preview.3.24172.9" />
<PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="9.0.0-preview.3" />
<PackageReference Include="SkiaSharp" Version="2.88.8" />
<PackageReference Include="SkiaSharp.NativeAssets.Linux" Version="2.88.8" />
</ItemGroup>

<ItemGroup>
<None Update="appsettings.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
</ItemGroup>

</Project>
74 changes: 56 additions & 18 deletions Boolean/Modules/FunUtils.cs
Original file line number Diff line number Diff line change
@@ -1,19 +1,57 @@
using Boolean.Util;
using Discord;
using Discord.Interactions;

namespace Boolean;

public class FunUtils : InteractionModuleBase<SocketInteractionContext>
{
[SlashCommand("execute", "Executes a fiendish individual.")]
public async Task Execute(IUser user, string? reason = null)
{
await RespondAsync(embed: new EmbedBuilder
{
Description = $"{user.Mention} has been executed by {Context.User.Mention}"
+ (reason != null ? $"\nReason: `{reason}`" : ""),
Color = EmbedColors.Normal,
}.Build());
}
using Boolean.Util;
using Discord;
using Discord.Interactions;
using SkiaSharp;

namespace Boolean;

public class FunUtils : InteractionModuleBase<SocketInteractionContext>
{
[SlashCommand("execute", "Executes a fiendish individual.")]
public async Task Execute(IUser user, string? reason = null)
{
await RespondAsync(embed: new EmbedBuilder
{
Description = $"{user.Mention} has been executed by {Context.User.Mention}"
+ (reason != null ? $"\nReason: `{reason}`" : ""),
Color = EmbedColors.Normal,
}.Build());
}

[SlashCommand("conatidrake", "Creates the drake preference meme BUT conaticus")]
public async Task Conatidrake(string top, string bottom)
{
try
{
var templateImage = SKImage.FromEncodedData("./images/Conatidrake.jpg");
using (var surface = SKSurface.Create(templateImage.Info))
{
surface.Canvas.DrawImage(templateImage, 0, 0);

var font = new SKPaint
{
TextSize = 50,
IsAntialias = true,
Color = new SKColor(0, 0, 0),
Style = SKPaintStyle.Fill,
};

var width = templateImage.Width;
var height = templateImage.Height;

var topRect = new SKRect(width / 2, 0, width, height / 2);
var bottomRect = new SKRect(width / 2, height / 2, width, height);

Text.DrawTextBox(surface.Canvas, top, topRect, font);
Text.DrawTextBox(surface.Canvas, bottom, bottomRect, font);

var stream = surface.Snapshot().Encode().AsStream();
await Context.Channel.SendFileAsync(stream, "conatidrake.png");
}
}
catch (Exception e)
{
Console.WriteLine(e);
}
}
}
145 changes: 73 additions & 72 deletions Boolean/Program.cs
Original file line number Diff line number Diff line change
@@ -1,73 +1,74 @@
using System.Reflection;
using Discord;
using Discord.Interactions;
using Discord.WebSocket;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;

namespace Boolean;

class Program
{
private static ServiceProvider _serviceProvider;
private static DiscordSocketClient _client;

public static async Task Main()
{
HostApplicationBuilder builder = Host.CreateApplicationBuilder();
Config config = builder.Configuration.Get<Config>()
?? throw new Exception("Failed to load valid config from appsettings.json, please refer to the README.md for instructions.");

builder.Services
.AddDbContext<DataContext>(options => options.UseNpgsql(config.GetConnectionString()));

// Only start the bot outside of design time (avoids app running during dotnet ef commands)
if (EF.IsDesignTime) {
_serviceProvider = builder.Services.BuildServiceProvider();
goto buildApp;
}

_client = new DiscordSocketClient(new DiscordSocketConfig
{
GatewayIntents = GatewayIntents.All,
UseInteractionSnowflakeDate = false, // Prevents a funny from happening when your OS clock is out of sync
MessageCacheSize = 100,
});

var interactionService = new InteractionService(_client.Rest);

builder.Services
.AddSingleton(interactionService)
.AddSingleton(_client)
.AddSingleton(config)
.AddSingleton<EventHandlers>();

_serviceProvider = builder.Services.BuildServiceProvider();

await _client.LoginAsync(TokenType.Bot, config.DiscordToken);
await _client.StartAsync();

await interactionService.AddModulesAsync(Assembly.GetEntryAssembly(), _serviceProvider);
AttachEventHandlers();

buildApp:
IHost app = builder.Build();
await app.RunAsync();
}

private static void AttachEventHandlers()
{
var eventHandlers = _serviceProvider.GetRequiredService<EventHandlers>();

_client.Log += eventHandlers.LogMessage;
_client.Ready += eventHandlers.Ready;
_client.InteractionCreated += eventHandlers.InteractionCreated;
_client.JoinedGuild += eventHandlers.GuildCreate;
_client.ButtonExecuted += eventHandlers.ButtonExecuted;
_client.ReactionAdded += eventHandlers.ReactionAdded;
_client.ReactionRemoved += eventHandlers.ReactionRemoved;
_client.UserJoined += eventHandlers.UserJoined;
}
using System.Reflection;
using Discord;
using Discord.Interactions;
using Discord.WebSocket;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;

namespace Boolean;

class Program
{
private static ServiceProvider _serviceProvider;
private static DiscordSocketClient _client;

public static async Task Main()
{
HostApplicationBuilder builder = Host.CreateApplicationBuilder();
Config config = builder.Configuration.Get<Config>()
?? throw new Exception("Failed to load valid config from appsettings.json, please refer to the README.md for instructions.");

builder.Services
.AddDbContext<DataContext>(options => options.UseNpgsql(config.GetConnectionString()));

// Only start the bot outside of design time (avoids app running during dotnet ef commands)
if (EF.IsDesignTime)
{
_serviceProvider = builder.Services.BuildServiceProvider();
goto buildApp;
}

_client = new DiscordSocketClient(new DiscordSocketConfig
{
GatewayIntents = GatewayIntents.All,
UseInteractionSnowflakeDate = false, // Prevents a funny from happening when your OS clock is out of sync
MessageCacheSize = 100,
});

var interactionService = new InteractionService(_client.Rest);

builder.Services
.AddSingleton(interactionService)
.AddSingleton(_client)
.AddSingleton(config)
.AddSingleton<EventHandlers>();

_serviceProvider = builder.Services.BuildServiceProvider();

await _client.LoginAsync(TokenType.Bot, config.DiscordToken);
await _client.StartAsync();

await interactionService.AddModulesAsync(Assembly.GetEntryAssembly(), _serviceProvider);
AttachEventHandlers();

buildApp:
IHost app = builder.Build();
await app.RunAsync();
}

private static void AttachEventHandlers()
{
var eventHandlers = _serviceProvider.GetRequiredService<EventHandlers>();

_client.Log += eventHandlers.LogMessage;
_client.Ready += eventHandlers.Ready;
_client.InteractionCreated += eventHandlers.InteractionCreated;
_client.JoinedGuild += eventHandlers.GuildCreate;
_client.ButtonExecuted += eventHandlers.ButtonExecuted;
_client.ReactionAdded += eventHandlers.ReactionAdded;
_client.ReactionRemoved += eventHandlers.ReactionRemoved;
_client.UserJoined += eventHandlers.UserJoined;
}
}
25 changes: 25 additions & 0 deletions Boolean/Utils/Drawing/Text.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
using SkiaSharp;

public static class Text
{
public static void DrawTextBox(SKCanvas canvas, string text, SKRect rect, SKPaint paint)
{
var spaceWidth = paint.MeasureText(" ");
var wordX = rect.Left;
var wordY = rect.Top + paint.TextSize;

foreach (var word in text.Split(' '))
{
var wordWidth = paint.MeasureText(word);

if (wordWidth > rect.Right - wordX)
{
wordY += paint.FontSpacing;
wordX = rect.Left;
}

canvas.DrawText(word, wordX, wordY, paint);
wordX += wordWidth + spaceWidth;
}
}
}
Binary file added Boolean/images/Conatidrake.jpg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.

0 comments on commit 9d2e262

Please sign in to comment.