pso2packetlib/protocol/
friends.rs

1//! Friend related packets. \[0x18\]
2use crate::fixed_types::FixedString;
3
4use super::{HelperReadWrite, PacketReadWrite};
5use std::time::Duration;
6
7// ----------------------------------------------------------------
8// Friend packets
9// ----------------------------------------------------------------
10
11/// (0x18, 0x14) Friend List Request.
12///
13/// (C -> S) Sent when a client wants a friend list.
14///
15/// Respond with: [`crate::protocol::Packet::FriendList`]
16#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
17#[cfg_attr(feature = "serde", serde(default))]
18#[derive(Debug, Clone, Default, PartialEq, PacketReadWrite)]
19#[Id(0x18, 0x14)]
20pub struct FriendListRequestPacket {
21    pub unk: u32,
22}
23
24/// (0x18, 0x15) Friend List.
25///
26/// (S -> C) Sent in response to a request.
27///
28/// Response to: [`crate::protocol::Packet::FriendListRequest`]
29#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
30#[cfg_attr(feature = "serde", serde(default))]
31#[derive(Debug, Clone, Default, PartialEq, PacketReadWrite)]
32#[Id(0x18, 0x15)]
33#[Flags(Flags::PACKED)]
34#[Magic(0x2E1E, 0x63)]
35pub struct FriendListPacket {
36    pub unk1: u32,
37    pub unk2: u16,
38    pub unk3: u16,
39    /// Players friends.
40    pub friends: Vec<FriendListEntry>,
41    /// Player nickname.
42    pub nickname: String,
43}
44
45/// (0x18, 0x18) Send Friend Request.
46///
47/// (C -> S) Sent when a client has sent a friend request to another player.
48///
49/// Respond with: [`crate::protocol::Packet::AddedRequest`]
50#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
51#[cfg_attr(feature = "serde", serde(default))]
52#[derive(Debug, Clone, Default, PartialEq, PacketReadWrite)]
53#[Id(0x18, 0x18)]
54#[Flags(Flags::PACKED)]
55#[Magic(0xBF57, 0x44)]
56pub struct SendFriendRequestPacket {
57    /// Target player ID.
58    pub id: u32,
59    /// Request message.
60    #[Seek(4)]
61    pub msg: String,
62}
63
64/// (0x18, 0x1A) Friend Request Sent.
65///
66/// (S -> C) Sent in response to a request.
67///
68/// Response to: [`crate::protocol::Packet::SendFriendRequest`]
69#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
70#[cfg_attr(feature = "serde", serde(default))]
71#[derive(Debug, Clone, Default, PartialEq, PacketReadWrite)]
72#[Id(0x18, 0x1A)]
73pub struct AddedRequestPacket {
74    pub unk1: u32,
75    /// Sender player ID.
76    pub sender_id: u32,
77    /// Target player ID.
78    #[Seek(4)]
79    pub target_id: u32,
80    /// Sender player nickname.
81    #[Seek(4)]
82    pub sender_nickname: FixedString<0x22>,
83    /// Target player nickname.
84    pub target_nickname: FixedString<0x22>,
85    /// Request message.
86    pub msg: FixedString<0x80>,
87    /// Request send timestamp.
88    pub send_time: Duration,
89    #[Seek(0x88)]
90    pub unk2: u8,
91    pub unk3: u8,
92    #[SeekAfter(0x91)]
93    pub unk4: u8,
94}
95
96// ----------------------------------------------------------------
97// Additional structs
98// ----------------------------------------------------------------
99
100/// Friend entry in friend list.
101#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
102#[cfg_attr(feature = "serde", serde(default))]
103#[derive(Debug, Clone, Default, PartialEq, HelperReadWrite)]
104pub struct FriendListEntry {
105    /// Player ID.
106    pub id: u32,
107    /// Player nickname.
108    #[Seek(4)]
109    pub nickname: FixedString<0x20>,
110    /// Player character name (if logged in).
111    #[Seek(4)]
112    pub char_name: FixedString<0x10>,
113    /// Friend flags.
114    #[Seek(4)]
115    pub flags: FriendFlags,
116    pub unk2: u8,
117    pub unk3: u8,
118    pub unk4: u8,
119    #[Seek(4)]
120    pub unk5: u32,
121    /// Player current block ID.
122    #[Seek(8)]
123    pub blockid: u32,
124    /// Player current location.
125    pub location: FriendLocation,
126    pub unk6: u16,
127    pub unk7: u32,
128    /// Player alliance name.
129    pub alliance_name: FixedString<0x18>,
130    #[Seek(0x8)]
131    pub unk8: Duration,
132    pub unk9: Duration,
133    #[Seek(0x38)]
134    pub unk10: u32,
135    #[Seek(4)]
136    pub unk11: u8,
137    pub unk12: u8,
138    #[Seek(2)]
139    #[SeekAfter(4)]
140    pub unk13: Duration,
141}
142
143bitflags::bitflags! {
144    /// Friend flags.
145    #[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
146    #[cfg_attr(feature = "serde", serde(default))]
147    #[derive(Debug, Copy, Clone, Default, PartialEq, HelperReadWrite)]
148    #[BitFlags(u8)]
149    pub struct FriendFlags: u8 {
150        /// Is the friend online.
151        const IS_ONLINE = 1 << 0;
152        /// Are login notifications enabled for this friend.
153        const LOGIN_NOTIF = 1 << 3;
154        /// Did the player not log in for a while.
155        const NO_RECENT_LOGINS = 1 << 5;
156
157        const _ = !0;
158    }
159}
160
161/// Friend map location.
162#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
163#[repr(u16)]
164#[derive(Debug, Copy, Clone, Default, PartialEq, HelperReadWrite)]
165pub enum FriendLocation {
166    /// Player is in the lobby.
167    #[default]
168    Lobby,
169    /// Player is in the quest map.
170    Quest,
171    /// Player is in the personal quarters.
172    PersonalQ,
173    /// Player is in the alliance quarters.
174    AllianceQ,
175    /// Player is in the casino.
176    Casino,
177    /// Player is in the challenger lobby.
178    ChallengerLobby,
179    /// Player is in the ARKS bridge.
180    Bridge,
181    /// Player is in the cafe.
182    FrancasCafe,
183    /// Player is in the battle lobby.
184    BattleLobby,
185
186    #[Read_default]
187    Unknown = 0xFFFF,
188}