1use serde::Serialize;
2
3pub mod natives;
4
5pub mod events {
6 use cfx_core::events::Event;
7 use futures::Stream;
8 use serde::{Deserialize, Serialize};
9
10 #[derive(Debug, Serialize, Deserialize)]
11 pub struct ClientGameTypeStart {
12 pub resource_name: String,
13 }
14
15 pub fn client_game_type_start<'a>() -> impl Stream<Item = Event<'a, ClientGameTypeStart>> {
16 cfx_core::events::subscribe("onClientGameTypeStart", cfx_core::events::EventScope::Local)
17 }
18}
19
20use cfx_core::runtime::sleep_for;
21use natives::{player::*, streaming::*, task::*};
22use std::time::Duration;
23
24#[derive(Debug)]
25pub struct TaskSequenceBuilder {
26 sequence: i32,
27}
28
29impl TaskSequenceBuilder {
30 pub fn new() -> TaskSequenceBuilder {
31 let mut sequence = 0;
32 open_sequence_task(&mut sequence);
33
34 TaskSequenceBuilder { sequence }
35 }
36
37 pub async fn play_anim<Dict, Name>(
38 self,
39 anim_dict: Dict,
40 anim_name: Name,
41 blend_in_speed: f32,
42 blend_out_speed: f32,
43 duration: i32,
44 flag: i32,
45 playback_rate: f32,
46 lock_x: bool,
47 lock_y: bool,
48 lock_z: bool,
49 ) -> Self
50 where
51 Dict: AsRef<str>,
52 Name: AsRef<str>,
53 {
54 let anim_dict = anim_dict.as_ref();
55 let anim_name = anim_name.as_ref();
56
57 request_anim_dict(anim_dict);
58
59 while !has_anim_dict_loaded(anim_dict) {
60 sleep_for(Duration::from_millis(5)).await;
61 }
62
63 task_play_anim(
64 0,
65 anim_dict,
66 anim_name,
67 blend_in_speed,
68 blend_out_speed,
69 duration,
70 flag,
71 playback_rate,
72 lock_x,
73 lock_y,
74 lock_z,
75 );
76
77 self
78 }
79
80 pub fn run(self, clear_tasks: bool) {
81 let ped = player_ped_id();
82
83 if clear_tasks {
84 clear_ped_tasks(ped);
85 }
86
87 close_sequence_task(self.sequence);
88 task_perform_sequence(ped, self.sequence);
89 }
90}
91
92impl Drop for TaskSequenceBuilder {
93 fn drop(&mut self) {
94 clear_sequence_task(&mut self.sequence);
95 }
96}
97
98pub fn emit_net<T: Serialize>(event_name: &str, payload: T) {
99 if let Ok(payload) = rmp_serde::to_vec(&payload) {
100 natives::cfx::trigger_server_event_internal(
101 event_name,
102 payload.as_slice(),
103 payload.len() as _,
104 );
105 }
106}