~ruther/NosSmooth

ref: 6de4f21874ea1ac10ee4079a74cb05a4ebcae39b NosSmooth/Core/NosSmooth.Game/PacketHandlers/Relations/GroupInitResponder.cs -rw-r--r-- 4.2 KiB
6de4f218 — Rutherther fix(game): add skills api to the service provider 2 years ago
                                                                                
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
//
//  GroupInitResponder.cs
//
//  Copyright (c) František Boháček. All rights reserved.
//  Licensed under the MIT license. See LICENSE file in the project root for full license information.

using System.Diagnostics;
using System.Linq.Expressions;
using NosSmooth.Core.Packets;
using NosSmooth.Game.Data.Info;
using NosSmooth.Game.Data.Social;
using NosSmooth.Game.Events.Core;
using NosSmooth.Game.Events.Groups;
using NosSmooth.Packets.Enums.Entities;
using NosSmooth.Packets.Server.Groups;
using Remora.Results;

namespace NosSmooth.Game.PacketHandlers.Relations;

/// <summary>
/// A group initialization responder.
/// </summary>
public class GroupInitResponder : IPacketResponder<PinitPacket>, IPacketResponder<PstPacket>
{
    private readonly Game _game;
    private readonly EventDispatcher _eventDispatcher;

    /// <summary>
    /// Initializes a new instance of the <see cref="GroupInitResponder"/> class.
    /// </summary>
    /// <param name="game">The game.</param>
    /// <param name="eventDispatcher">The event dispatcher.</param>
    public GroupInitResponder(Game game, EventDispatcher eventDispatcher)
    {
        _game = game;
        _eventDispatcher = eventDispatcher;
    }

    /// <inheritdoc />
    public async Task<Result> Respond(PacketEventArgs<PinitPacket> packetArgs, CancellationToken ct = default)
    {
        var packet = packetArgs.Packet;

        Group BuildGroup(Group? group)
        {
            var members = packet.PinitSubPackets?
                .Where(x => x.PlayerSubPacket is not null)
                .OrderBy(x => x.PlayerSubPacket!.GroupPosition)
                .Select(e => CreateEntity(e, group?.Members))
                .ToList() ?? new List<GroupMember>();

            return new Group(null, members);
        }

        var group = await _game.CreateOrUpdateGroupAsync
        (
            () => BuildGroup(null),
            BuildGroup,
            ct: ct
        );

        if (group is null)
        {
            throw new UnreachableException();
        }

        return await _eventDispatcher.DispatchEvent(new GroupInitializedEvent(group), ct);
    }

    /// <inheritdoc />
    public async Task<Result> Respond(PacketEventArgs<PstPacket> packetArgs, CancellationToken ct = default)
    {
        var packet = packetArgs.Packet;
        if (packet.EntityType != EntityType.Player)
        {
            return Result.FromSuccess();
        }

        GroupMember? member = null;
        await _game.CreateOrUpdateGroupAsync
        (
            () => null,
            g =>
            {
                member = g.Members?.FirstOrDefault(x => x.PlayerId == packet.EntityId);

                if (member is not null)
                {
                    member.Hp = new Health { Amount = packet.Hp, Percentage = packet.HpPercentage };
                    member.Mp = new Health { Amount = packet.Mp, Percentage = packet.MpPercentage };
                    member.Class = packet.PlayerClass ?? member.Class;
                    member.Sex = packet.PlayerSex ?? member.Sex;
                    member.EffectsVNums = packet.Effects?.Select(x => x.CardId).ToList();
                    member.MorphVNum = packet.PlayerMorphVNum ?? member.MorphVNum;
                }

                return g;
            },
            ct: ct
        );

        if (member is not null)
        {
            await _eventDispatcher.DispatchEvent
            (
                new GroupMemberStatEvent(member),
                ct
            );
        }

        return Result.FromSuccess();
    }

    private GroupMember CreateEntity(PinitSubPacket packet, IReadOnlyList<GroupMember>? members)
    {
        var playerSubPacket = packet.PlayerSubPacket!;
        var originalMember = members?.FirstOrDefault(x => x.PlayerId == packet.EntityId);

        return new(packet.EntityId)
        {
            Level = playerSubPacket.Level,
            HeroLevel = playerSubPacket.HeroLevel,
            Name = playerSubPacket.Name?.Name,
            Class = playerSubPacket.Class,
            Sex = playerSubPacket.Sex,
            MorphVNum = playerSubPacket.MorphVNum,
            Hp = originalMember?.Hp,
            Mp = originalMember?.Mp,
            EffectsVNums = originalMember?.EffectsVNums
        };
    }
}
Do not follow this link