CS2-Kit
C++23 library for CS2 Metamod:Source plugin development
Loading...
Searching...
No Matches
ConVarService.cpp
Go to the documentation of this file.
1#include <CS2Kit/Sdk/ConVarService.hpp>
2#include <CS2Kit/Sdk/GameInterfaces.hpp>
3#include <CS2Kit/Utils/Log.hpp>
4#include <icvar.h>
5#include <tier1/convar.h>
6
7namespace
8{
9
10void GlobalConVarChangeCallback(ConVarRefAbstract* ref, CSplitScreenSlot /*slot*/, const char* newValue,
11 const char* oldValue, void* /*unk*/)
12{
13 if (!ref)
14 return;
15
16 const char* name = ref->GetName();
17 CS2Kit::Sdk::ConVarService::Instance().DispatchChange(name, oldValue, newValue);
18}
19
20} // namespace
21
22namespace CS2Kit::Sdk
23{
24using namespace CS2Kit::Utils;
25
26bool ConVarService::Initialize()
27{
28 if (!GameInterfaces::Instance().CVar)
29 {
30 Log::Error("ConVarService: ICvar not available.");
31 return false;
32 }
33
34 Log::Info("ConVar service initialized.");
35 return true;
36}
37
38std::optional<int> ConVarService::GetInt(const char* name) const
39{
40 ConVarRefAbstract ref(name);
41 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
42 return std::nullopt;
43
44 return ref.GetInt();
45}
46
47std::optional<float> ConVarService::GetFloat(const char* name) const
48{
49 ConVarRefAbstract ref(name);
50 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
51 return std::nullopt;
52
53 return ref.GetFloat();
54}
55
56std::optional<std::string> ConVarService::GetString(const char* name) const
57{
58 ConVarRefAbstract ref(name);
59 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
60 return std::nullopt;
61
62 CUtlString str = ref.GetString();
63 return std::string(str.Get());
64}
65
66std::optional<bool> ConVarService::GetBool(const char* name) const
67{
68 ConVarRefAbstract ref(name);
69 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
70 return std::nullopt;
71
72 return ref.GetBool();
73}
74
75bool ConVarService::Exists(const char* name) const
76{
77 ConVarRefAbstract ref(name);
78 return ref.IsValidRef() && ref.IsConVarDataAvailable();
79}
80
81bool ConVarService::SetInt(const char* name, int value)
82{
83 ConVarRefAbstract ref(name);
84 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
85 return false;
86
87 ref.SetInt(value);
88 return true;
89}
90
91bool ConVarService::SetFloat(const char* name, float value)
92{
93 ConVarRefAbstract ref(name);
94 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
95 return false;
96
97 ref.SetFloat(value);
98 return true;
99}
100
101bool ConVarService::SetString(const char* name, const char* value)
102{
103 ConVarRefAbstract ref(name);
104 if (!ref.IsValidRef() || !ref.IsConVarDataAvailable())
105 return false;
106
107 ref.SetString(CUtlString(value));
108 return true;
109}
110
111void ConVarService::ExecuteServerCommand(const char* command)
112{
113 auto* engine = GameInterfaces::Instance().Engine;
114 if (!engine)
115 {
116 Log::Warn("ConVarService::ExecuteServerCommand: IVEngineServer2 not available.");
117 return;
118 }
119
120 engine->ServerCommand(command);
121}
122
123uint64_t ConVarService::OnChange(ChangeCallback callback)
124{
125 if (!_globalCallbackInstalled)
126 {
127 auto* cvar = GameInterfaces::Instance().CVar;
128 if (cvar)
129 {
130 cvar->InstallGlobalChangeCallback(&GlobalConVarChangeCallback);
131 _globalCallbackInstalled = true;
132 }
133 }
134
135 uint64_t id = _nextCallbackId++;
136 _changeCallbacks[id] = std::move(callback);
137 return id;
138}
139
140void ConVarService::RemoveChangeListener(uint64_t id)
141{
142 _changeCallbacks.erase(id);
143}
144
145void ConVarService::DispatchChange(const char* name, const char* oldValue, const char* newValue)
146{
147 for (auto& [id, callback] : _changeCallbacks)
148 {
149 callback(name, oldValue, newValue);
150 }
151}
152
153} // namespace CS2Kit::Sdk