Complete devtool, added support for vehicle weapon sync.
This commit is contained in:
@ -7,45 +7,178 @@ using GTA;
|
||||
using GTA.Math;
|
||||
using System.Drawing;
|
||||
using System.Windows.Forms;
|
||||
using System.Threading;
|
||||
|
||||
namespace RageCoop.Client
|
||||
{
|
||||
internal class DevTool:Script
|
||||
{
|
||||
public static Entity ToMark;
|
||||
public static Vehicle ToMark;
|
||||
public static bool UseSecondary=false;
|
||||
public static int Current = 0;
|
||||
public static int Secondary = 0;
|
||||
public static MuzzleDir Direction = MuzzleDir.Forward;
|
||||
public DevTool()
|
||||
{
|
||||
Tick+=OnTick;
|
||||
KeyUp+=OnKeyUp;
|
||||
KeyDown+=OnKeyDown;
|
||||
}
|
||||
|
||||
private void OnKeyUp(object sender, KeyEventArgs e)
|
||||
private void OnKeyDown(object sender, KeyEventArgs e)
|
||||
{
|
||||
switch (e.KeyCode)
|
||||
{
|
||||
case Keys.Right:
|
||||
Current++;
|
||||
DebugMenu.boneIndexItem.AltTitle= Current.ToString();
|
||||
break;
|
||||
case Keys.Left:
|
||||
Current--;
|
||||
DebugMenu.boneIndexItem.AltTitle= Current.ToString();
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (ToMark==null||(!ToMark.Exists())) { return; }
|
||||
if (DevToolMenu.Menu.SelectedItem==DevToolMenu.boneIndexItem) {
|
||||
|
||||
private void OnTick(object sender, EventArgs e)
|
||||
switch (e.KeyCode)
|
||||
{
|
||||
case Keys.Right:
|
||||
Current++;
|
||||
break;
|
||||
case Keys.Left:
|
||||
Current--;
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if (DevToolMenu.Menu.SelectedItem==DevToolMenu.secondaryBoneIndexItem)
|
||||
{
|
||||
|
||||
switch (e.KeyCode)
|
||||
{
|
||||
case Keys.Right:
|
||||
Secondary++;
|
||||
break;
|
||||
case Keys.Left:
|
||||
Secondary--;
|
||||
break;
|
||||
}
|
||||
}
|
||||
Update();
|
||||
}
|
||||
private static void Update()
|
||||
{
|
||||
|
||||
if (Current>ToMark.Bones.Count-1)
|
||||
{
|
||||
Current=0;
|
||||
}
|
||||
else if (Current< 0)
|
||||
{
|
||||
Current=ToMark.Bones.Count-1;
|
||||
}
|
||||
DevToolMenu.boneIndexItem.AltTitle= Current.ToString();
|
||||
if (Secondary>ToMark.Bones.Count-1)
|
||||
{
|
||||
Secondary=0;
|
||||
}
|
||||
else if (Secondary< 0)
|
||||
{
|
||||
Secondary=ToMark.Bones.Count-1;
|
||||
}
|
||||
DevToolMenu.secondaryBoneIndexItem.AltTitle= Secondary.ToString();
|
||||
}
|
||||
private static void OnTick(object sender, EventArgs e)
|
||||
{
|
||||
if(ToMark == null || !ToMark.Exists()){ return;}
|
||||
if ((Current< 0)||(Current>ToMark.Bones.Count-1)) {
|
||||
Current=0;
|
||||
DebugMenu.boneIndexItem.AltTitle= Current.ToString();
|
||||
Update();
|
||||
Draw(Current);
|
||||
if (UseSecondary)
|
||||
{
|
||||
Draw(Secondary);
|
||||
}
|
||||
var bone = ToMark.Bones[Current];
|
||||
|
||||
}
|
||||
private static void Draw(int boneindex)
|
||||
{
|
||||
var bone = ToMark.Bones[boneindex];
|
||||
World.DrawLine(bone.Position, bone.Position+2*bone.ForwardVector, Color.Blue);
|
||||
World.DrawLine(bone.Position, bone.Position+2*bone.UpVector, Color.Green);
|
||||
World.DrawLine(bone.Position, bone.Position+2*bone.RightVector, Color.Yellow);
|
||||
Vector3 todraw = bone.ForwardVector;
|
||||
switch ((byte)Direction)
|
||||
{
|
||||
case 0:
|
||||
todraw=bone.ForwardVector;
|
||||
break;
|
||||
case 1:
|
||||
todraw=bone.RightVector;
|
||||
break;
|
||||
case 2:
|
||||
todraw=bone.UpVector;
|
||||
break;
|
||||
case 3:
|
||||
todraw=bone.ForwardVector*-1;
|
||||
break;
|
||||
case 4:
|
||||
todraw=bone.RightVector*-1;
|
||||
break;
|
||||
case 5:
|
||||
todraw=bone.UpVector*-1;
|
||||
break;
|
||||
}
|
||||
World.DrawLine(bone.Position, bone.Position+10*todraw, Color.Red);
|
||||
}
|
||||
public static void CopyToClipboard(MuzzleDir dir)
|
||||
{
|
||||
|
||||
if (ToMark!=null)
|
||||
{
|
||||
string s;
|
||||
if (UseSecondary)
|
||||
{
|
||||
if ((byte)dir<3)
|
||||
{
|
||||
s=$@"
|
||||
// {ToMark.DisplayName}
|
||||
case {ToMark.Model.Hash}:
|
||||
i=Main.Ticked%2==0 ? {Current} : {Secondary};
|
||||
return new MuzzleInfo(v.Bones[i].Position, v.Bones[i].{dir}Vector);
|
||||
";
|
||||
}
|
||||
else
|
||||
{
|
||||
s=$@"
|
||||
// {ToMark.DisplayName}
|
||||
case {ToMark.Model.Hash}:
|
||||
i=Main.Ticked%2==0 ? {Current} : {Secondary};
|
||||
return new MuzzleInfo(v.Bones[i].Position, v.Bones[i].{((MuzzleDir)(dir-3)).ToString()}Vector*-1);
|
||||
";
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if ((byte)dir<3)
|
||||
{
|
||||
s=$@"
|
||||
// {ToMark.DisplayName}
|
||||
case {ToMark.Model.Hash}:
|
||||
return new MuzzleInfo(v.Bones[{Current}].Position, v.Bones[{Current}].{dir}Vector);
|
||||
";
|
||||
}
|
||||
else
|
||||
{
|
||||
s=$@"
|
||||
// {ToMark.DisplayName}
|
||||
case {ToMark.Model.Hash}:
|
||||
return new MuzzleInfo(v.Bones[{Current}].Position, v.Bones[{Current}].{((MuzzleDir)(dir-3)).ToString()}Vector*-1);
|
||||
";
|
||||
}
|
||||
}
|
||||
Thread thread = new Thread(() => Clipboard.SetText(s));
|
||||
thread.SetApartmentState(ApartmentState.STA); //Set the thread to STA
|
||||
thread.Start();
|
||||
thread.Join();
|
||||
GTA.UI.Notification.Show("Copied to clipboard, please paste it on the GitHub issue page!");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
public enum MuzzleDir:byte
|
||||
{
|
||||
Forward=0,
|
||||
Right = 1,
|
||||
Up=2,
|
||||
Backward=3,
|
||||
Left = 4,
|
||||
Down=5,
|
||||
}
|
||||
}
|
||||
|
@ -196,7 +196,7 @@ namespace RageCoop.Client
|
||||
if (MainMenu.MenuPool.AreAnyVisible)
|
||||
{
|
||||
MainMenu.MainMenu.Visible = false;
|
||||
MainMenu.SubSettings.MainMenu.Visible = false;
|
||||
MainMenu.SubSettings.Menu.Visible = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -51,14 +51,17 @@ namespace RageCoop.Client.Menus
|
||||
MainMenu.Add(_usernameItem);
|
||||
MainMenu.Add(ServerIpItem);
|
||||
MainMenu.Add(_serverConnectItem);
|
||||
|
||||
MainMenu.AddSubMenu(SubSettings.MainMenu);
|
||||
MainMenu.AddSubMenu(DebugMenu.MainMenu);
|
||||
MainMenu.Add(_aboutItem);
|
||||
|
||||
MainMenu.AddSubMenu(SubSettings.Menu);
|
||||
MainMenu.AddSubMenu(DevToolMenu.Menu);
|
||||
MainMenu.AddSubMenu(DebugMenu.Menu);
|
||||
|
||||
|
||||
MenuPool.Add(MainMenu);
|
||||
MenuPool.Add(SubSettings.MainMenu);
|
||||
MenuPool.Add(DebugMenu.MainMenu);
|
||||
MenuPool.Add(SubSettings.Menu);
|
||||
MenuPool.Add(DevToolMenu.Menu);
|
||||
MenuPool.Add(DebugMenu.Menu);
|
||||
MenuPool.Add(DebugMenu.DiagnosticMenu);
|
||||
}
|
||||
|
||||
@ -106,7 +109,7 @@ namespace RageCoop.Client.Menus
|
||||
MainMenu.Items[1].Enabled = true;
|
||||
MainMenu.Items[2].Enabled = true;
|
||||
MainMenu.Items[2].Title = "Connect";
|
||||
SubSettings.MainMenu.Items[1].Enabled = false;
|
||||
SubSettings.Menu.Items[1].Enabled = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -6,12 +6,13 @@ using System.Threading.Tasks;
|
||||
using LemonUI;
|
||||
using LemonUI.Menus;
|
||||
using GTA;
|
||||
using System.Drawing;
|
||||
|
||||
namespace RageCoop.Client
|
||||
{
|
||||
internal static class DebugMenu
|
||||
{
|
||||
public static NativeMenu MainMenu = new NativeMenu("RAGECOOP", "Debug", "Debug settings") {
|
||||
public static NativeMenu Menu = new NativeMenu("RAGECOOP", "Debug", "Debug settings") {
|
||||
UseMouse = false,
|
||||
Alignment = Main.Settings.FlipMenu ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left
|
||||
};
|
||||
@ -21,24 +22,22 @@ namespace RageCoop.Client
|
||||
Alignment = Main.Settings.FlipMenu ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left
|
||||
};
|
||||
private static NativeItem d1=new NativeItem("PositionPrediction");
|
||||
private static NativeCheckboxItem devToolItem=new NativeCheckboxItem("DevTool");
|
||||
public static NativeItem boneIndexItem = new NativeItem("Current bone index");
|
||||
static DebugMenu()
|
||||
{
|
||||
Menu.Banner.Color = Color.FromArgb(225, 0, 0, 0);
|
||||
Menu.Title.Color = Color.FromArgb(255, 165, 0);
|
||||
|
||||
d1.Activated+=(sender,e) =>
|
||||
{
|
||||
try{ SyncParameters.PositioinPrediction =float.Parse(Game.GetUserInput(WindowTitle.EnterMessage20, SyncParameters.PositioinPrediction.ToString(), 20));}
|
||||
catch { }
|
||||
Update();
|
||||
};
|
||||
devToolItem.Activated+=DevToolItem_Activated;
|
||||
devToolItem.Checked=false;
|
||||
|
||||
|
||||
MainMenu.Add(d1);
|
||||
MainMenu.Add(devToolItem);
|
||||
MainMenu.Add(boneIndexItem);
|
||||
MainMenu.AddSubMenu(DiagnosticMenu);
|
||||
MainMenu.Opening+=(sender, e) =>Update();
|
||||
Menu.Add(d1);
|
||||
Menu.AddSubMenu(DiagnosticMenu);
|
||||
Menu.Opening+=(sender, e) =>Update();
|
||||
DiagnosticMenu.Opening+=(sender, e) =>
|
||||
{
|
||||
DiagnosticMenu.Clear();
|
||||
@ -52,17 +51,7 @@ namespace RageCoop.Client
|
||||
Update();
|
||||
}
|
||||
|
||||
private static void DevToolItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
if (devToolItem.Checked)
|
||||
{
|
||||
DevTool.ToMark=Game.Player.Character.CurrentVehicle;
|
||||
}
|
||||
else
|
||||
{
|
||||
DevTool.ToMark=null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static void Update()
|
||||
{
|
||||
|
88
Client/Menus/Sub/DevToolMenu.cs
Normal file
88
Client/Menus/Sub/DevToolMenu.cs
Normal file
@ -0,0 +1,88 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using LemonUI.Menus;
|
||||
using GTA;
|
||||
using System.Drawing;
|
||||
|
||||
namespace RageCoop.Client
|
||||
{
|
||||
internal class DevToolMenu
|
||||
{
|
||||
public static NativeMenu Menu = new NativeMenu("RAGECOOP", "DevTool", "Help with the development")
|
||||
{
|
||||
UseMouse = false,
|
||||
Alignment = Main.Settings.FlipMenu ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left
|
||||
};
|
||||
private static NativeCheckboxItem enableItem = new NativeCheckboxItem("Enable");
|
||||
|
||||
private static NativeCheckboxItem enableSecondaryItem = new NativeCheckboxItem("Secondary","Enable if this vehicle have two muzzles");
|
||||
public static NativeItem boneIndexItem = new NativeItem("Current bone index");
|
||||
public static NativeItem secondaryBoneIndexItem = new NativeItem("Secondary bone index");
|
||||
public static NativeItem clipboardItem = new NativeItem("Copy to clipboard");
|
||||
public static NativeListItem<MuzzleDir> dirItem = new NativeListItem<MuzzleDir>("Direction");
|
||||
static DevToolMenu()
|
||||
{
|
||||
Menu.Banner.Color = Color.FromArgb(225, 0, 0, 0);
|
||||
Menu.Title.Color = Color.FromArgb(255, 165, 0);
|
||||
|
||||
enableItem.Activated+=enableItem_Activated;
|
||||
enableItem.Checked=false;
|
||||
enableSecondaryItem.CheckboxChanged+=EnableSecondaryItem_Changed;
|
||||
|
||||
secondaryBoneIndexItem.Enabled=false;
|
||||
clipboardItem.Activated+=ClipboardItem_Activated;
|
||||
dirItem.ItemChanged+=DirItem_ItemChanged;
|
||||
foreach (var d in Enum.GetValues(typeof(MuzzleDir)))
|
||||
{
|
||||
dirItem.Items.Add((MuzzleDir)d);
|
||||
}
|
||||
dirItem.SelectedIndex=0;
|
||||
|
||||
Menu.Add(enableItem);
|
||||
Menu.Add(boneIndexItem);
|
||||
Menu.Add(enableSecondaryItem);
|
||||
Menu.Add(secondaryBoneIndexItem);
|
||||
Menu.Add(dirItem);
|
||||
Menu.Add(clipboardItem);
|
||||
}
|
||||
|
||||
private static void EnableSecondaryItem_Changed(object sender, EventArgs e)
|
||||
{
|
||||
if (enableSecondaryItem.Checked)
|
||||
{
|
||||
DevTool.UseSecondary=true;
|
||||
secondaryBoneIndexItem.Enabled=true;
|
||||
}
|
||||
else
|
||||
{
|
||||
DevTool.UseSecondary=false;
|
||||
secondaryBoneIndexItem.Enabled=false;
|
||||
}
|
||||
}
|
||||
|
||||
private static void DirItem_ItemChanged(object sender, ItemChangedEventArgs<MuzzleDir> e)
|
||||
{
|
||||
DevTool.Direction=dirItem.SelectedItem;
|
||||
}
|
||||
|
||||
private static void ClipboardItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
DevTool.CopyToClipboard(dirItem.SelectedItem);
|
||||
}
|
||||
|
||||
private static void enableItem_Activated(object sender, EventArgs e)
|
||||
{
|
||||
if (enableItem.Checked)
|
||||
{
|
||||
DevTool.ToMark=Game.Player.Character.CurrentVehicle;
|
||||
}
|
||||
else
|
||||
{
|
||||
DevTool.ToMark=null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -11,7 +11,7 @@ namespace RageCoop.Client.Menus.Sub
|
||||
/// </summary>
|
||||
public class SettingsMenu
|
||||
{
|
||||
public NativeMenu MainMenu = new NativeMenu("RAGECOOP", "Settings", "Go to the settings")
|
||||
public NativeMenu Menu = new NativeMenu("RAGECOOP", "Settings", "Go to the settings")
|
||||
{
|
||||
UseMouse = false,
|
||||
Alignment = Main.Settings.FlipMenu ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left
|
||||
@ -32,8 +32,8 @@ namespace RageCoop.Client.Menus.Sub
|
||||
/// </summary>
|
||||
public SettingsMenu()
|
||||
{
|
||||
MainMenu.Banner.Color = Color.FromArgb(225, 0, 0, 0);
|
||||
MainMenu.Title.Color = Color.FromArgb(255, 165, 0);
|
||||
Menu.Banner.Color = Color.FromArgb(225, 0, 0, 0);
|
||||
Menu.Title.Color = Color.FromArgb(255, 165, 0);
|
||||
|
||||
_disableTrafficItem.CheckboxChanged += DisableTrafficCheckboxChanged;
|
||||
_disablePauseAlt.CheckboxChanged+=_disablePauseAlt_CheckboxChanged;
|
||||
@ -43,13 +43,13 @@ namespace RageCoop.Client.Menus.Sub
|
||||
_passengerKey.Activated+=ChangePassengerKey;
|
||||
_vehicleSoftLimit.Activated+=vehicleSoftLimit_Activated;
|
||||
|
||||
MainMenu.Add(_disableTrafficItem);
|
||||
MainMenu.Add(_disablePauseAlt);
|
||||
MainMenu.Add(_flipMenuItem);
|
||||
MainMenu.Add(_showNetworkInfoItem);
|
||||
MainMenu.Add(_menuKey);
|
||||
MainMenu.Add(_passengerKey);
|
||||
MainMenu.Add(_vehicleSoftLimit);
|
||||
Menu.Add(_disableTrafficItem);
|
||||
Menu.Add(_disablePauseAlt);
|
||||
Menu.Add(_flipMenuItem);
|
||||
Menu.Add(_showNetworkInfoItem);
|
||||
Menu.Add(_menuKey);
|
||||
Menu.Add(_passengerKey);
|
||||
Menu.Add(_vehicleSoftLimit);
|
||||
}
|
||||
|
||||
|
||||
@ -109,7 +109,7 @@ namespace RageCoop.Client.Menus.Sub
|
||||
{
|
||||
Main.MainMenu.MainMenu.Alignment = _flipMenuItem.Checked ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left;
|
||||
|
||||
MainMenu.Alignment = _flipMenuItem.Checked ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left;
|
||||
Menu.Alignment = _flipMenuItem.Checked ? GTA.UI.Alignment.Right : GTA.UI.Alignment.Left;
|
||||
Main.Settings.FlipMenu = _flipMenuItem.Checked;
|
||||
Util.SaveSettings();
|
||||
}
|
||||
|
@ -470,31 +470,7 @@ namespace RageCoop.Client
|
||||
return (VehicleSeat)Function.Call<int>(Hash.GET_SEAT_PED_IS_TRYING_TO_ENTER, p);
|
||||
}
|
||||
|
||||
public static Vector3 GetMuzzlePosition(this Ped p)
|
||||
{
|
||||
var w = p.Weapons.CurrentWeaponObject;
|
||||
if (w!=null)
|
||||
{
|
||||
var hash = p.Weapons.Current.Hash;
|
||||
if (MuzzleBoneIndexes.ContainsKey(hash)) { return w.Bones[MuzzleBoneIndexes[hash]].Position; }
|
||||
return w.Position;
|
||||
}
|
||||
return p.Bones[Bone.SkelRightHand].Position;
|
||||
}
|
||||
|
||||
public static bool IsUsingProjectileWeapon(this Ped p)
|
||||
{
|
||||
var vp = p.VehicleWeapon;
|
||||
if (vp!=VehicleWeaponHash.Invalid)
|
||||
{
|
||||
return VehicleProjectileWeapons.Contains(vp);
|
||||
}
|
||||
else
|
||||
{
|
||||
var w = p.Weapons.Current;
|
||||
return w.Group==WeaponGroup.Thrown || ProjectileWeapons.Contains(w.Hash);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#endregion
|
||||
|
||||
@ -809,111 +785,10 @@ namespace RageCoop.Client
|
||||
}
|
||||
|
||||
|
||||
public static readonly Model[] WeaponModels = Weapon.GetAllModels();
|
||||
|
||||
[DllImport("kernel32.dll")]
|
||||
public static extern ulong GetTickCount64();
|
||||
public static int GetDamage(this Weapon w)
|
||||
{
|
||||
int damage=0;
|
||||
switch (w.Group)
|
||||
{
|
||||
case WeaponGroup.AssaultRifle: damage=30;break;
|
||||
case WeaponGroup.Heavy: damage=30;break;
|
||||
case WeaponGroup.MG: damage=30;break;
|
||||
case WeaponGroup.PetrolCan: damage=0;break;
|
||||
case WeaponGroup.Pistol: damage=30;break;
|
||||
case WeaponGroup.Shotgun: damage=30; break;
|
||||
case WeaponGroup.SMG: damage=20; break;
|
||||
case WeaponGroup.Sniper: damage=100; break;
|
||||
case WeaponGroup.Thrown: damage=0; break;
|
||||
case WeaponGroup.Unarmed: damage=0; break;
|
||||
}
|
||||
return damage;
|
||||
}
|
||||
public static readonly Dictionary<WeaponHash, int> MuzzleBoneIndexes = new Dictionary<WeaponHash, int>
|
||||
{
|
||||
{WeaponHash.HeavySniper,6},
|
||||
{WeaponHash.MarksmanRifle,9},
|
||||
{WeaponHash.SniperRifle,9},
|
||||
{WeaponHash.AdvancedRifle,5},
|
||||
{WeaponHash.SpecialCarbine,9},
|
||||
{WeaponHash.BullpupRifle,7},
|
||||
{WeaponHash.AssaultRifle,9},
|
||||
{WeaponHash.CarbineRifle,6},
|
||||
{WeaponHash.MachinePistol,5},
|
||||
{WeaponHash.SMG,5},
|
||||
{WeaponHash.AssaultSMG,6},
|
||||
{WeaponHash.CombatPDW,5},
|
||||
{WeaponHash.MG,6},
|
||||
{WeaponHash.CombatMG,7},
|
||||
{WeaponHash.Gusenberg,7},
|
||||
{WeaponHash.MicroSMG,10},
|
||||
{WeaponHash.APPistol,8},
|
||||
{WeaponHash.StunGun,4},
|
||||
{WeaponHash.Pistol,8},
|
||||
{WeaponHash.CombatPistol,8},
|
||||
{WeaponHash.Pistol50,7},
|
||||
{WeaponHash.SNSPistol,8},
|
||||
{WeaponHash.HeavyPistol,8},
|
||||
{WeaponHash.VintagePistol,8},
|
||||
{WeaponHash.Railgun,9},
|
||||
{WeaponHash.Minigun,5},
|
||||
{WeaponHash.Musket,3},
|
||||
{WeaponHash.HeavyShotgun,10},
|
||||
{WeaponHash.PumpShotgun,11},
|
||||
{WeaponHash.SawnOffShotgun,8},
|
||||
{WeaponHash.BullpupShotgun,8},
|
||||
{WeaponHash.AssaultShotgun,9},
|
||||
{WeaponHash.HeavySniperMk2,11},
|
||||
{WeaponHash.MarksmanRifleMk2,9},
|
||||
{WeaponHash.CarbineRifleMk2,13},
|
||||
{WeaponHash.SpecialCarbineMk2,16},
|
||||
{WeaponHash.BullpupRifleMk2,8},
|
||||
{WeaponHash.CompactRifle,7},
|
||||
{WeaponHash.MilitaryRifle,11},
|
||||
{WeaponHash.AssaultrifleMk2,17},
|
||||
{WeaponHash.MiniSMG,5},
|
||||
{WeaponHash.SMGMk2,6},
|
||||
{WeaponHash.CombatMGMk2,16},
|
||||
{WeaponHash.UnholyHellbringer,4},
|
||||
{WeaponHash.PistolMk2,12},
|
||||
{WeaponHash.SNSPistolMk2,15},
|
||||
{WeaponHash.CeramicPistol,10},
|
||||
{WeaponHash.MarksmanPistol,4},
|
||||
{WeaponHash.Revolver,7},
|
||||
{WeaponHash.RevolverMk2,7},
|
||||
{WeaponHash.DoubleActionRevolver,7},
|
||||
{WeaponHash.NavyRevolver,7},
|
||||
{WeaponHash.PericoPistol,4},
|
||||
{WeaponHash.FlareGun,4},
|
||||
{WeaponHash.UpNAtomizer,4},
|
||||
{WeaponHash.HomingLauncher,5},
|
||||
{WeaponHash.CompactGrenadeLauncher,8},
|
||||
{WeaponHash.Widowmaker,6},
|
||||
{WeaponHash.GrenadeLauncher,3},
|
||||
{WeaponHash.RPG,9},
|
||||
{WeaponHash.DoubleBarrelShotgun,8},
|
||||
{WeaponHash.SweeperShotgun,7},
|
||||
{WeaponHash.CombatShotgun,7},
|
||||
{WeaponHash.PumpShotgunMk2,7},
|
||||
|
||||
};
|
||||
public static readonly HashSet<WeaponHash> ProjectileWeapons = new HashSet<WeaponHash> {
|
||||
WeaponHash.HomingLauncher,
|
||||
WeaponHash.RPG,
|
||||
WeaponHash.Firework,
|
||||
WeaponHash.UpNAtomizer,
|
||||
WeaponHash.GrenadeLauncher,
|
||||
WeaponHash.GrenadeLauncherSmoke,
|
||||
WeaponHash.CompactGrenadeLauncher,
|
||||
WeaponHash.FlareGun,
|
||||
};
|
||||
public static readonly HashSet<VehicleWeaponHash> VehicleProjectileWeapons = new HashSet<VehicleWeaponHash> {
|
||||
VehicleWeaponHash.PlaneRocket,
|
||||
VehicleWeaponHash.SpaceRocket,
|
||||
VehicleWeaponHash.Tank,
|
||||
};
|
||||
|
||||
}
|
||||
/// <summary>
|
||||
///
|
||||
|
186
Client/Misc/WeaponUtil.cs
Normal file
186
Client/Misc/WeaponUtil.cs
Normal file
@ -0,0 +1,186 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using GTA;
|
||||
using GTA.Math;
|
||||
|
||||
namespace RageCoop.Client
|
||||
{
|
||||
internal class MuzzleInfo
|
||||
{
|
||||
public MuzzleInfo(Vector3 pos,Vector3 forward)
|
||||
{
|
||||
Position = pos;
|
||||
ForawardVector=forward;
|
||||
}
|
||||
public Vector3 Position;
|
||||
public Vector3 ForawardVector;
|
||||
}
|
||||
internal static class WeaponUtil
|
||||
{
|
||||
public static Vector3 GetMuzzlePosition(this Ped p)
|
||||
{
|
||||
var w = p.Weapons.CurrentWeaponObject;
|
||||
if (w!=null)
|
||||
{
|
||||
var hash = p.Weapons.Current.Hash;
|
||||
if (MuzzleBoneIndexes.ContainsKey(hash)) { return w.Bones[MuzzleBoneIndexes[hash]].Position; }
|
||||
return w.Position;
|
||||
}
|
||||
return p.Bones[Bone.SkelRightHand].Position;
|
||||
}
|
||||
public static MuzzleInfo GetMuzzleInfo(this Vehicle v)
|
||||
{
|
||||
int i;
|
||||
switch (v.Model.Hash)
|
||||
{
|
||||
// BUZZARD
|
||||
case 788747387:
|
||||
i=Main.Ticked%2==0 ? 28 : 23;
|
||||
return new MuzzleInfo(v.Bones[i].Position, v.Bones[i].ForwardVector);
|
||||
|
||||
// ANNIHL
|
||||
case 837858166:
|
||||
i=(int)Main.Ticked%4+35;
|
||||
return new MuzzleInfo(v.Bones[i].Position, v.Bones[i].ForwardVector);
|
||||
|
||||
// HYDRA
|
||||
case 970385471:
|
||||
i=Main.Ticked%2==0 ? 29 : 28;
|
||||
return new MuzzleInfo(v.Bones[i].Position, v.Bones[i].ForwardVector);
|
||||
|
||||
// STARLING
|
||||
case -1700874274:
|
||||
i=Main.Ticked%2==0 ? 24 : 12;
|
||||
return new MuzzleInfo(v.Bones[i].Position, v.Bones[i].ForwardVector);
|
||||
|
||||
// RHINO
|
||||
case 782665360:
|
||||
return new MuzzleInfo(v.Bones[35].Position,v.Bones[35].ForwardVector);
|
||||
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
public static bool IsUsingProjectileWeapon(this Ped p)
|
||||
{
|
||||
var vp = p.VehicleWeapon;
|
||||
if (vp!=VehicleWeaponHash.Invalid)
|
||||
{
|
||||
return VehicleProjectileWeapons.Contains(vp);
|
||||
}
|
||||
else
|
||||
{
|
||||
var w = p.Weapons.Current;
|
||||
return w.Group==WeaponGroup.Thrown || ProjectileWeapons.Contains(w.Hash);
|
||||
}
|
||||
}
|
||||
|
||||
public static int GetDamage(this Weapon w)
|
||||
{
|
||||
int damage = 0;
|
||||
switch (w.Group)
|
||||
{
|
||||
case WeaponGroup.AssaultRifle: damage=30; break;
|
||||
case WeaponGroup.Heavy: damage=30; break;
|
||||
case WeaponGroup.MG: damage=30; break;
|
||||
case WeaponGroup.PetrolCan: damage=0; break;
|
||||
case WeaponGroup.Pistol: damage=30; break;
|
||||
case WeaponGroup.Shotgun: damage=30; break;
|
||||
case WeaponGroup.SMG: damage=20; break;
|
||||
case WeaponGroup.Sniper: damage=100; break;
|
||||
case WeaponGroup.Thrown: damage=0; break;
|
||||
case WeaponGroup.Unarmed: damage=0; break;
|
||||
}
|
||||
return damage;
|
||||
}
|
||||
public static readonly Dictionary<WeaponHash, int> MuzzleBoneIndexes = new Dictionary<WeaponHash, int>
|
||||
{
|
||||
{WeaponHash.HeavySniper,6},
|
||||
{WeaponHash.MarksmanRifle,9},
|
||||
{WeaponHash.SniperRifle,9},
|
||||
{WeaponHash.AdvancedRifle,5},
|
||||
{WeaponHash.SpecialCarbine,9},
|
||||
{WeaponHash.BullpupRifle,7},
|
||||
{WeaponHash.AssaultRifle,9},
|
||||
{WeaponHash.CarbineRifle,6},
|
||||
{WeaponHash.MachinePistol,5},
|
||||
{WeaponHash.SMG,5},
|
||||
{WeaponHash.AssaultSMG,6},
|
||||
{WeaponHash.CombatPDW,5},
|
||||
{WeaponHash.MG,6},
|
||||
{WeaponHash.CombatMG,7},
|
||||
{WeaponHash.Gusenberg,7},
|
||||
{WeaponHash.MicroSMG,10},
|
||||
{WeaponHash.APPistol,8},
|
||||
{WeaponHash.StunGun,4},
|
||||
{WeaponHash.Pistol,8},
|
||||
{WeaponHash.CombatPistol,8},
|
||||
{WeaponHash.Pistol50,7},
|
||||
{WeaponHash.SNSPistol,8},
|
||||
{WeaponHash.HeavyPistol,8},
|
||||
{WeaponHash.VintagePistol,8},
|
||||
{WeaponHash.Railgun,9},
|
||||
{WeaponHash.Minigun,5},
|
||||
{WeaponHash.Musket,3},
|
||||
{WeaponHash.HeavyShotgun,10},
|
||||
{WeaponHash.PumpShotgun,11},
|
||||
{WeaponHash.SawnOffShotgun,8},
|
||||
{WeaponHash.BullpupShotgun,8},
|
||||
{WeaponHash.AssaultShotgun,9},
|
||||
{WeaponHash.HeavySniperMk2,11},
|
||||
{WeaponHash.MarksmanRifleMk2,9},
|
||||
{WeaponHash.CarbineRifleMk2,13},
|
||||
{WeaponHash.SpecialCarbineMk2,16},
|
||||
{WeaponHash.BullpupRifleMk2,8},
|
||||
{WeaponHash.CompactRifle,7},
|
||||
{WeaponHash.MilitaryRifle,11},
|
||||
{WeaponHash.AssaultrifleMk2,17},
|
||||
{WeaponHash.MiniSMG,5},
|
||||
{WeaponHash.SMGMk2,6},
|
||||
{WeaponHash.CombatMGMk2,16},
|
||||
{WeaponHash.UnholyHellbringer,4},
|
||||
{WeaponHash.PistolMk2,12},
|
||||
{WeaponHash.SNSPistolMk2,15},
|
||||
{WeaponHash.CeramicPistol,10},
|
||||
{WeaponHash.MarksmanPistol,4},
|
||||
{WeaponHash.Revolver,7},
|
||||
{WeaponHash.RevolverMk2,7},
|
||||
{WeaponHash.DoubleActionRevolver,7},
|
||||
{WeaponHash.NavyRevolver,7},
|
||||
{WeaponHash.PericoPistol,4},
|
||||
{WeaponHash.FlareGun,4},
|
||||
{WeaponHash.UpNAtomizer,4},
|
||||
{WeaponHash.HomingLauncher,5},
|
||||
{WeaponHash.CompactGrenadeLauncher,8},
|
||||
{WeaponHash.Widowmaker,6},
|
||||
{WeaponHash.GrenadeLauncher,3},
|
||||
{WeaponHash.RPG,9},
|
||||
{WeaponHash.DoubleBarrelShotgun,8},
|
||||
{WeaponHash.SweeperShotgun,7},
|
||||
{WeaponHash.CombatShotgun,7},
|
||||
{WeaponHash.PumpShotgunMk2,7},
|
||||
|
||||
};
|
||||
|
||||
|
||||
public static readonly HashSet<WeaponHash> ProjectileWeapons = new HashSet<WeaponHash> {
|
||||
WeaponHash.HomingLauncher,
|
||||
WeaponHash.RPG,
|
||||
WeaponHash.Firework,
|
||||
WeaponHash.UpNAtomizer,
|
||||
WeaponHash.GrenadeLauncher,
|
||||
WeaponHash.GrenadeLauncherSmoke,
|
||||
WeaponHash.CompactGrenadeLauncher,
|
||||
WeaponHash.FlareGun,
|
||||
};
|
||||
public static readonly HashSet<VehicleWeaponHash> VehicleProjectileWeapons = new HashSet<VehicleWeaponHash> {
|
||||
VehicleWeaponHash.PlaneRocket,
|
||||
VehicleWeaponHash.SpaceRocket,
|
||||
VehicleWeaponHash.Tank,
|
||||
};
|
||||
}
|
||||
}
|
@ -122,6 +122,8 @@
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="DevTools\DevTool.cs" />
|
||||
<Compile Include="Menus\Sub\DevToolMenu.cs" />
|
||||
<Compile Include="Misc\WeaponUtil.cs" />
|
||||
<Compile Include="Networking\Chat.cs" />
|
||||
<Compile Include="COOPAPI.cs" />
|
||||
<Compile Include="Debug.cs" />
|
||||
|
@ -168,7 +168,7 @@ namespace RageCoop.Client
|
||||
{
|
||||
|
||||
SyncedPed c = Passengers[seat];
|
||||
if ((c!=null)&&c.MainPed!=null&&(!currentPassengers.ContainsKey(i))) {
|
||||
if ((c!=null)&&c.MainPed!=null&&(!currentPassengers.ContainsKey(i))&&(!c.MainPed.IsBeingJacked)) {
|
||||
Passengers[seat].MainPed.SetIntoVehicle(MainVehicle, seat);
|
||||
}
|
||||
}
|
||||
|
@ -318,7 +318,7 @@ namespace RageCoop.Client
|
||||
{
|
||||
|
||||
/// Prevent projectiles from exploding next to vehicle
|
||||
if (Util.VehicleProjectileWeapons.Contains((VehicleWeaponHash)p.MainProjectile.WeaponHash))
|
||||
if (WeaponUtil.VehicleProjectileWeapons.Contains((VehicleWeaponHash)p.MainProjectile.WeaponHash))
|
||||
{
|
||||
if (p.MainProjectile.WeaponHash!=(WeaponHash)VehicleWeaponHash.Tank && p.Origin.DistanceTo(p.MainProjectile.Position)<2)
|
||||
{
|
||||
|
@ -87,9 +87,25 @@ namespace RageCoop.Client {
|
||||
}, ConnectionChannel.SyncEvents);
|
||||
}
|
||||
|
||||
public static void TriggerVehBulletShot(uint hash, Vehicle veh)
|
||||
public static void TriggerVehBulletShot(uint hash, Vehicle veh, SyncedPed owner)
|
||||
{
|
||||
if (hash==(uint)VehicleWeaponHash.PlayerBuzzard)
|
||||
{
|
||||
hash=(uint)WeaponHash.HeavyRifle;
|
||||
}
|
||||
// ANNIHL
|
||||
if (veh.Model.Hash==837858166)
|
||||
{
|
||||
Networking.SendBulletShot(veh.Bones[35].Position, veh.Bones[35].Position+veh.Bones[35].ForwardVector,hash,owner.ID);
|
||||
Networking.SendBulletShot(veh.Bones[36].Position, veh.Bones[36].Position+veh.Bones[36].ForwardVector,hash, owner.ID);
|
||||
Networking.SendBulletShot(veh.Bones[37].Position, veh.Bones[37].Position+veh.Bones[37].ForwardVector,hash, owner.ID);
|
||||
Networking.SendBulletShot(veh.Bones[38].Position, veh.Bones[38].Position+veh.Bones[38].ForwardVector,hash, owner.ID);
|
||||
return;
|
||||
}
|
||||
|
||||
var info = veh.GetMuzzleInfo();
|
||||
if (info==null) { Main.Logger.Warning($"Failed to get muzzle info for vehicle:{veh.DisplayName}");return; }
|
||||
Networking.SendBulletShot(info.Position,info.Position+info.ForawardVector,hash,owner.ID);
|
||||
}
|
||||
|
||||
#endregion
|
||||
@ -248,26 +264,50 @@ namespace RageCoop.Client {
|
||||
public static void Check(SyncedPed c)
|
||||
{
|
||||
Ped subject = c.MainPed;
|
||||
if (subject.IsShooting && !subject.IsUsingProjectileWeapon())
|
||||
if (subject.IsShooting)
|
||||
{
|
||||
int i = 0;
|
||||
Func<bool> getBulletImpact = (() =>
|
||||
if (!subject.IsUsingProjectileWeapon())
|
||||
{
|
||||
Vector3 endPos = subject.LastWeaponImpactPosition;
|
||||
if (endPos==default )
|
||||
int i = 0;
|
||||
Func<bool> getBulletImpact = (() =>
|
||||
{
|
||||
if (i>5)
|
||||
Vector3 endPos = subject.LastWeaponImpactPosition;
|
||||
if (endPos==default)
|
||||
{
|
||||
if (i>5)
|
||||
{
|
||||
endPos=subject.GetAimCoord();
|
||||
if (subject.IsInVehicle() && subject.VehicleWeapon!=VehicleWeaponHash.Invalid)
|
||||
{
|
||||
if (subject.IsOnTurretSeat())
|
||||
{
|
||||
TriggerBulletShot((uint)subject.VehicleWeapon, subject.GetSyncEntity(), endPos);
|
||||
}
|
||||
else
|
||||
{
|
||||
TriggerVehBulletShot((uint)subject.VehicleWeapon, subject.CurrentVehicle,c);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
TriggerBulletShot((uint)subject.Weapons.Current.Hash, subject.GetSyncEntity(), endPos);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
i++;
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
endPos=subject.GetAimCoord();
|
||||
if (subject.IsInVehicle() && subject.VehicleWeapon!=VehicleWeaponHash.Invalid)
|
||||
{
|
||||
if (subject.IsOnTurretSeat())
|
||||
{
|
||||
TriggerBulletShot((uint)subject.VehicleWeapon,subject.GetSyncEntity(), endPos);
|
||||
TriggerBulletShot((uint)subject.VehicleWeapon, subject.GetSyncEntity(), endPos);
|
||||
}
|
||||
else
|
||||
{
|
||||
TriggerVehBulletShot((uint)subject.VehicleWeapon, subject.CurrentVehicle);
|
||||
TriggerVehBulletShot((uint)subject.VehicleWeapon, subject.CurrentVehicle,c);
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -276,37 +316,21 @@ namespace RageCoop.Client {
|
||||
}
|
||||
return true;
|
||||
}
|
||||
i++;
|
||||
return false;
|
||||
}
|
||||
else
|
||||
|
||||
|
||||
});
|
||||
if (!getBulletImpact())
|
||||
{
|
||||
if (subject.IsInVehicle() && subject.VehicleWeapon!=VehicleWeaponHash.Invalid)
|
||||
{
|
||||
if (subject.IsOnTurretSeat())
|
||||
{
|
||||
TriggerBulletShot((uint)subject.VehicleWeapon, subject.GetSyncEntity(), endPos);
|
||||
}
|
||||
else
|
||||
{
|
||||
TriggerVehBulletShot((uint)subject.VehicleWeapon, subject.CurrentVehicle);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
TriggerBulletShot((uint)subject.Weapons.Current.Hash, subject.GetSyncEntity(), endPos);
|
||||
}
|
||||
return true;
|
||||
Main.QueueAction(getBulletImpact);
|
||||
}
|
||||
|
||||
|
||||
});
|
||||
if (!getBulletImpact())
|
||||
}
|
||||
else if (subject.VehicleWeapon==VehicleWeaponHash.Tank && subject.LastWeaponImpactPosition!=default)
|
||||
{
|
||||
Main.QueueAction(getBulletImpact);
|
||||
TriggerBulletShot((uint)VehicleWeaponHash.Tank, subject.GetSyncEntity(),subject.LastWeaponImpactPosition);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
// Vehicles
|
||||
var g = subject.IsGettingIntoVehicle;
|
||||
|
@ -35,13 +35,14 @@ namespace RageCoop.Client
|
||||
return;
|
||||
}
|
||||
|
||||
if (Networking.IsOnServer)
|
||||
if (!Networking.IsOnServer)
|
||||
{
|
||||
Game.DisableControlThisFrame(Control.FrontendPause);
|
||||
if (Main.Settings.DisableAlternatePause)
|
||||
{
|
||||
Game.DisableControlThisFrame(Control.FrontendPauseAlternate);
|
||||
}
|
||||
return ;
|
||||
}
|
||||
Game.DisableControlThisFrame(Control.FrontendPause);
|
||||
if (Main.Settings.DisableAlternatePause)
|
||||
{
|
||||
Game.DisableControlThisFrame(Control.FrontendPauseAlternate);
|
||||
}
|
||||
|
||||
// Sets a value that determines how aggressive the ocean waves will be.
|
||||
|
Reference in New Issue
Block a user