【问题标题】:C# Assign role to user if playing game如果玩游戏,C#将角色分配给用户
【发布时间】:2021-12-26 03:59:21
【问题描述】:

如果正在玩特定游戏,我正在尝试通过机器人分配 Discord 角色。

这是我的代码:

    private async Task UserUpdated(SocketGuildUser before, SocketGuildUser after)
    {
        //fetch guild and user by id
        ulong long2 = ulong.Parse(after.Id.ToString());
        var user = _client.GetGuild(myguildid).GetUser(long2);
        var Game = user.Activity as Game;
        if (user.IsBot) { return; }

        //check if playing a game with the name mygamename          
        if (Game.Name == "mygamename")
        {
            //if so, assign the role
            SocketGuild socketGuild = after.Guild;
            SocketRole socketRole = socketGuild.GetRole(myroleid);
            await after.AddRoleAsync(socketRole);
        }
        //Check if user isn't playing game with name mygamename
        else if (Game.Name != "mygamename")
        {
            //If so, remove role
            SocketGuild socketGuild = after.Guild;
            SocketRole socketRole = socketGuild.GetRole(myroleid);
            await after.RemoveRoleAsync(socketRole);
        }
    }

但是,如果我尝试使用名称 mygamename 玩游戏,它会分配角色,但如果我停止播放,则会在此行中出现错误:

if (Game.Name == "mygamename")

它抛出了这个错误:

20:31:10 网关 GuildMemberUpdated 处理程序抛出了一个 未处理的异常。:System.NullReferenceException:对象引用 未设置为对象的实例。在 myprogram.Program.d__6.MoveNext() 在 C:\Users\User\Desktop\myprogram\myprogram\Program.cs:第 9 行 --- 从先前抛出异常的位置结束堆栈跟踪 --- 在 System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(任务 任务)在 System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(任务 任务)在 Discord.EventExtensions.d__2`2.MoveNext() --- 从先前抛出异常的位置结束堆栈跟踪 --- 在 System.Runtime.CompilerServices.TaskAwaiter.ThrowForNonSuccess(任务 任务)在 System.Runtime.CompilerServices.TaskAwaiter.HandleNonSuccessAndDebuggerNotification(任务 任务)在 Discord.WebSocket.DiscordSocketClient.d__139.MoveNext()

而且它没有分配角色。我怎么能解决这个问题?有没有更好的方法来获取之前/之后并检查正在玩的游戏?

【问题讨论】:

  • user.Activity as Game 显然会产生null。活动是游戏吗?
  • @OlivierJacot-Descombes 活动本身是一个自定义的丰富存在,但它显示为游戏。
  • 使用is 模式匹配来确保它是Game
  • @DanielA.White 它给了我“'bool' 不包含 'Name' 的定义”
  • 如果他们完全停止玩游戏,User.Game 不会为空吗?在这种情况下,您应该只删除 else 分支上的 if

标签: c# discord discord.net


【解决方案1】:

也许不需要强制转换为Game 类型? Game 对象默认具有 ActivityType 属性和 Playing 值。所以你可以先试试IActivity,它有Playing活动类型和Name你的游戏:

var game = userAfter.Activities.FirstOrDefault(activity => activity.Type == ActivityType.Playing
                                                        && activity.Name == "MyGameName");

如果您的游戏名称没有任何Playing 活动,则game 变量将为空,因此您只需检查is not null

private async Task UserUpdated(SocketGuildUser userBefore, SocketGuildUser userAfter)
{
    if (userAfter.IsBot)
        return;

    var myRoleID = 123123123UL;
    var role = userAfter.Guild.GetRole(myRoleID);
    var game = userAfter.Activities.FirstOrDefault(activity => activity.Type == ActivityType.Playing
                                                            && activity.Name == "MyGameName");

    if (game != null)
    {
        // No need to add AddRole, if user already have it
        if (!userAfter.Roles.Contains(role))
            await userAfter.AddRoleAsync(role);
    }
    else
    {
        // No need to call RemoveRole, if user haven't it
        if (userAfter.Roles.Contains(role))
            await userAfter.RemoveRoleAsync(role);
    }         
}

没有自己测试代码示例,但你可以试试。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-09-13
    • 2023-02-14
    • 1970-01-01
    • 2018-06-13
    • 2022-11-25
    • 2015-08-01
    相关资源
    最近更新 更多