Skip to content

Commit 7f110b6

Browse files
authored
Merge pull request #231 from SourceDotNET/lua
Lua
2 parents a30fdab + 436106d commit 7f110b6

76 files changed

Lines changed: 3055 additions & 131 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎Game.Client/C_BaseAnimating.cs‎

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,10 @@ public void SetBodygroup(int group, int value) {
8282
Animation.SetBodygroup(GetModelPtr(), ref Body, group, value);
8383
}
8484

85+
public int GetBodygroup(int group) => Animation.GetBodygroup(GetModelPtr(), Body, group);
86+
public ReadOnlySpan<char> GetBodygroupName(int group) => Animation.GetBodygroupName(GetModelPtr(), group);
87+
public int GetBodygroupCount(int group) => Animation.GetBodygroupCount(GetModelPtr(), group);
88+
8589
float GroundSpeed;
8690
const TimeUnit_t MAX_ANIMTIME_INTERVAL = 0.2;
8791
public TimeUnit_t GetAnimTimeInterval() => Math.Min(gpGlobals.CurTime - AnimTime, MAX_ANIMTIME_INTERVAL);
@@ -179,7 +183,7 @@ public void StudioFrameAdvance() {
179183
GroundSpeed = (float)GetSequenceGroundSpeed(hdr, GetSequence()) * GetModelScale();
180184
}
181185

182-
public override int VPhysicsGetObjectList(Span<IPhysicsObject?> list){
186+
public override int VPhysicsGetObjectList(Span<IPhysicsObject?> list) {
183187
if (IsRagdoll()) {
184188
int i;
185189
for (i = 0; i < Ragdoll.RagdollBoneCount(); ++i) {
@@ -845,7 +849,7 @@ public string GetSequenceName(int sequence) {
845849
return Animation.GetSequenceName(GetModelPtr(), sequence);
846850
}
847851

848-
public ClientRagdoll? Ragdoll = null;
852+
public ClientRagdoll? Ragdoll = null;
849853

850854
public override void OnDataChanged(DataUpdateType updateType) {
851855
if (Ragdoll != null && GetSequence() != PrevSequence) {
@@ -1043,6 +1047,8 @@ public static class SequenceProxy
10431047
for (i = 0; i < hdr.GetNumPoseParameters(); i++) {
10441048
MStudioPoseParamDesc Pose = hdr.PoseParameter(i);
10451049
iv_flPoseParameter.SetLooping(Pose.Loop != 0.0f, i);
1050+
if (!IsServerEntity())
1051+
SetPoseParameter(hdr, i, 0.0f);
10461052
}
10471053

10481054
EyeAttachment = LookupAttachment("eyes");

‎Game.Client/C_BaseEntity.cs‎

Lines changed: 29 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -876,6 +876,7 @@ public C_BaseEntity() {
876876
public int Health;
877877
[NetworkVar("m_iMaxHealth")]
878878
public int MaxHealth;
879+
public virtual int GetMaxHealth() => MaxHealth;
879880
[NetworkVar("m_spawnflags")]
880881
public int SpawnFlags;
881882
[NetworkVar("m_iGModFlags")]
@@ -1246,7 +1247,29 @@ public bool SetModel(ReadOnlySpan<char> modelName) {
12461247

12471248
public virtual ref readonly Vector3 GetRenderOrigin() => ref GetAbsOrigin();
12481249
public virtual ref readonly QAngle GetRenderAngles() => ref GetAbsAngles();
1250+
#if GMOD_DLL
1251+
Vector3 RenderBoundsOverrideMins;
1252+
Vector3 RenderBoundsOverrideMaxs;
1253+
bool HasRenderBoundsOverride;
1254+
1255+
public virtual void SetRenderBounds(in Vector3 mins, in Vector3 maxs) {
1256+
RenderBoundsOverrideMins = mins;
1257+
RenderBoundsOverrideMaxs = maxs;
1258+
HasRenderBoundsOverride = true;
1259+
}
1260+
1261+
public virtual bool GetRenderBoundsOverride(out Vector3 mins, out Vector3 maxs) {
1262+
mins = RenderBoundsOverrideMins;
1263+
maxs = RenderBoundsOverrideMaxs;
1264+
return HasRenderBoundsOverride;
1265+
}
1266+
#endif
1267+
12491268
public void GetRenderBounds(out Vector3 mins, out Vector3 maxs) {
1269+
#if GMOD_DLL
1270+
if (GetRenderBoundsOverride(out mins, out maxs))
1271+
return;
1272+
#endif
12501273
ModelType nModelType = modelinfo.GetModelType(Model);
12511274
if (nModelType == ModelType.Studio || nModelType == ModelType.Brush)
12521275
modelinfo.GetModelRenderBounds(GetModel(), out mins, out maxs);
@@ -1274,6 +1297,10 @@ public virtual bool IsTransparent() {
12741297
}
12751298

12761299
public virtual void UpdateOnRemove() {
1300+
#if GMOD_DLL
1301+
if (GetRefEHandle().Index != Constants.INVALID_EHANDLE_INDEX)
1302+
garrysmod.EntityRemoved(this, DestroyedOnRecreateEntities);
1303+
#endif
12771304
VPhysicsDestroyObject();
12781305

12791306
Assert(GetMoveParent() == null);
@@ -2536,7 +2563,7 @@ public void MoveToAimEnt() {
25362563
public bool IsDormant() => IsServerEntity() && Dormant;
25372564

25382565
[MethodImpl(MethodImplOptions.AggressiveInlining)]
2539-
private bool IsServerEntity() => Index != -1;
2566+
public bool IsServerEntity() => Index != -1;
25402567

25412568
public int EntIndex() {
25422569
return Index;
@@ -3538,7 +3565,7 @@ public bool GetShadowCastDistance(ref float dist, ShadowType shadowType) {
35383565

35393566
EHANDLE ShadowDirUseOtherEntity = new();
35403567

3541-
public bool GetShadowCastDirection(ref Vector3 direction, ShadowType shadowType) {
3568+
public virtual bool GetShadowCastDirection(ref Vector3 direction, ShadowType shadowType) {
35423569
if (ShadowDirUseOtherEntity.Get() != null)
35433570
return ShadowDirUseOtherEntity.Get()!.GetShadowCastDirection(ref direction, shadowType);
35443571
return false;

‎Game.Client/C_BasePlayer.cs‎

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -106,6 +106,11 @@ public bool GetSteamID(out CSteamID id) {
106106
}
107107
return false;
108108
}
109+
public int GetUserID() {
110+
if (!engine.GetPlayerInfo(EntIndex(), out PlayerInfo pi))
111+
return -1;
112+
return pi.UserID;
113+
}
109114
PlayerInfo NetworkIDInfo;
110115
InlineArray33<char> NetworkIDString;
111116
public ReadOnlySpan<char> GetNetworkIDString() {
@@ -123,7 +128,7 @@ public ReadOnlySpan<char> GetNetworkIDString() {
123128
return "NULL";
124129
}
125130
public bool IsHLTV() => IsLocalPlayer() && engine.IsHLTV();
126-
public bool IsBot() => false; // TODO, gmod
131+
public bool IsBot() => (GetFlags() & EntityFlags.FakeClient) != 0;
127132
public static bool ShouldDrawLocalPlayer() {
128133
return input.CAM_IsThirdPerson(); // todo
129134
}
@@ -621,6 +626,7 @@ public void SetLocalViewAngles(in QAngle angles) {
621626
EHANDLE TonemapController = new();
622627
[NetworkVar("m_hViewEntity")]
623628
EHANDLE ViewEntity = new();
629+
public virtual C_BaseEntity? GetViewEntity() => ViewEntity.Get();
624630
[NetworkVar("m_hViewModel")]
625631
InlineArrayNewMaxViewmodels<Handle<C_BaseViewModel>> ViewModel = new();
626632
[NetworkVar("m_bDisableWorldClicking")]

‎Game.Client/C_PlayerResource.cs‎

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,32 @@ public bool IsConnected(int index) {
7171
return Connected[index];
7272
}
7373

74+
public int GetPlayerScore(int index) {
75+
if (!IsConnected(index))
76+
return 0;
77+
return Score[index];
78+
}
79+
80+
public int GetPing(int index) {
81+
if (!IsConnected(index))
82+
return 0;
83+
return Ping[index];
84+
}
85+
86+
public int GetDeaths(int index) {
87+
if (!IsConnected(index))
88+
return 0;
89+
return Deaths[index];
90+
}
91+
92+
public int GetFrags(int index) => GetPlayerScore(index);
93+
94+
public int GetArmor(int index) {
95+
if (!IsConnected(index))
96+
return 0;
97+
return Armor[index];
98+
}
99+
74100
public ReadOnlySpan<char> GetPlayerName(int index) {
75101
if (index < 1 || index > Constants.MAX_PLAYERS) {
76102
Assert(false);
Lines changed: 148 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,148 @@
1+
using Source;
2+
using Source.Common.GUI;
3+
using Source.GUI.Controls;
4+
5+
using Steamworks;
6+
7+
namespace Game.Client.GarrysMod;
8+
9+
public class AvatarImage : Panel
10+
{
11+
static readonly List<TextureID>[] FreeTextures = [[], [], []];
12+
13+
TextureID TextureID;
14+
ulong SteamID;
15+
int Size;
16+
readonly IImage? DefaultImage;
17+
18+
readonly Callback<AvatarImageLoaded_t> AvatarImageLoaded;
19+
readonly Callback<PersonaStateChange_t> PersonaStateChange;
20+
21+
public AvatarImage(Panel? parent, ReadOnlySpan<char> name) : base(parent, name) {
22+
SteamID = 0;
23+
Size = 0;
24+
AvatarImageLoaded = Callback<AvatarImageLoaded_t>.Create(OnAvatarImageLoaded);
25+
PersonaStateChange = Callback<PersonaStateChange_t>.Create(OnPersonaStateChange);
26+
TextureID = TextureID.INVALID;
27+
DefaultImage = SchemeManager.GetImage("avatar_default", true);
28+
}
29+
30+
public override void Dispose() {
31+
ClearTexture();
32+
PersonaStateChange.Dispose();
33+
AvatarImageLoaded.Dispose();
34+
base.Dispose();
35+
}
36+
37+
void OnAvatarImageLoaded(AvatarImageLoaded_t info) {
38+
if (info.m_steamID.m_SteamID == SteamID)
39+
LoadAvatar();
40+
}
41+
42+
void OnPersonaStateChange(PersonaStateChange_t info) {
43+
if (info.m_ulSteamID == SteamID && (info.m_nChangeFlags & EPersonaChange.k_EPersonaChangeAvatar) != 0)
44+
LoadAvatar();
45+
}
46+
47+
void ClearTexture() {
48+
SteamID = 0;
49+
if (TextureID == TextureID.INVALID) {
50+
TextureID = TextureID.INVALID;
51+
return;
52+
}
53+
54+
FreeTextures[Size].Add(TextureID);
55+
TextureID = TextureID.INVALID;
56+
}
57+
58+
void LoadAvatar() {
59+
CSteamID steamID = new(SteamID);
60+
if (SteamFriends.RequestUserInformation(steamID, false))
61+
return;
62+
63+
int avatar;
64+
if (Size == 0)
65+
avatar = SteamFriends.GetSmallFriendAvatar(steamID);
66+
else if (Size == 1)
67+
avatar = SteamFriends.GetMediumFriendAvatar(steamID);
68+
else if (Size == 2)
69+
avatar = SteamFriends.GetLargeFriendAvatar(steamID);
70+
else
71+
return;
72+
73+
if ((uint)(avatar + 1) <= 1)
74+
return;
75+
76+
if (!SteamUtils.GetImageSize(avatar, out uint wide, out uint tall))
77+
return;
78+
79+
int size = (int)(wide * tall * 4);
80+
byte[] rgba = new byte[size];
81+
if (!SteamUtils.GetImageRGBA(avatar, rgba, size))
82+
return;
83+
84+
if (TextureID == TextureID.INVALID) {
85+
List<TextureID> free = FreeTextures[Size];
86+
if (free.Count < 1)
87+
TextureID = Surface.CreateNewTextureID(true);
88+
else {
89+
TextureID = free[^1];
90+
free.RemoveAt(free.Count - 1);
91+
}
92+
}
93+
94+
Surface.DrawSetTextureRGBA(TextureID, rgba, (int)wide, (int)tall, 0, true);
95+
}
96+
97+
public void SetSteamID(ulong steamID, int size) {
98+
if (size < 0)
99+
size = 0;
100+
else if (2 < size)
101+
size = 2;
102+
103+
if (SteamID != steamID || size != Size) {
104+
if (size != Size)
105+
ClearTexture();
106+
SteamID = steamID;
107+
Size = size;
108+
LoadAvatar();
109+
}
110+
}
111+
112+
public void SetPlayer(C_BasePlayer? player, int size) {
113+
if (player == null || !player.GetSteamID(out CSteamID id)) {
114+
ClearTexture();
115+
return;
116+
}
117+
118+
ulong steamID = id.m_SteamID;
119+
int clamped = 0;
120+
if (-1 < size) {
121+
clamped = size;
122+
if (2 < size)
123+
clamped = 2;
124+
}
125+
126+
if (SteamID == steamID && clamped == Size)
127+
return;
128+
129+
if (clamped != Size)
130+
ClearTexture();
131+
132+
SteamID = steamID;
133+
Size = clamped;
134+
LoadAvatar();
135+
}
136+
137+
public override void Paint() {
138+
if (TextureID == TextureID.INVALID) {
139+
DefaultImage!.SetSize(GetWide(), GetTall());
140+
DefaultImage.Paint();
141+
return;
142+
}
143+
144+
Surface.DrawSetTexture(TextureID);
145+
Surface.DrawSetColor(new Color(255, 255, 255, 255));
146+
Surface.DrawTexturedRect(0, 0, GetWide(), GetTall());
147+
}
148+
}

0 commit comments

Comments
 (0)