Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- using System;
- using System.Drawing;
- using System.Windows.Forms;
- using GTA;
- using GTA.Math;
- using GTA.Native;
- using NativeUI;
- using Control = GTA.Control;
- namespace BennysMotorworks
- {
- public enum CameraPosition
- {
- Car,
- Interior,
- Engine,
- Trunk,
- FrontBumper,
- RearBumper,
- Grille,
- Tank,
- Plaque,
- BackPlate,
- FrontPlate,
- Wheels,
- }
- public enum CameraRotationMode
- {
- Around,
- FirstPerson,
- }
- public class WorkshopCamera
- {
- private Camera _mainCamera;
- private bool _isDragging;
- private PointF _dragOffset;
- private Entity _target;
- private Vector3 _targetPos;
- private CameraPosition _internalCameraPosition;
- // LERPING
- public bool IsLerping;
- private DateTime startTime;
- private float duration;
- private Vector3 startValuePosition;
- private Vector3 endValuePosition;
- private Vector3 startValueRotation;
- private Vector3 endValueRotation;
- public CameraPosition MainCameraPosition
- {
- get
- {
- return _internalCameraPosition;
- }
- set
- {
- OnCameraChange(value);
- _internalCameraPosition = value;
- }
- }
- public CameraRotationMode RotationMode { get; set; }
- public float CameraZoom
- {
- get { return _cameraZoom; }
- set
- {
- if (_mainCamera != null)
- {
- var dir = CutsceneManager.RotationToDirection(_mainCamera.Rotation);
- _mainCamera.Position += dir*(_cameraZoom - value);
- }
- _cameraZoom = value;
- }
- }
- public CameraClamp CameraClamp { get; set; }
- private void OnCameraChange(CameraPosition newPos)
- {
- switch (newPos)
- {
- case CameraPosition.Car:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- if ((_internalCameraPosition != CameraPosition.Car && _internalCameraPosition != CameraPosition.Interior))
- {
- _mainCamera.PointAt(_target);
- _targetPos = _target.Position;
- _cameraZoom = 5f;
- RotationMode = CameraRotationMode.Around;
- CameraClamp = new CameraClamp() { MaxVerticalValue = -40f, MinVerticalValue = -3f };
- _mainCamera.Shake(CameraShake.Hand, 0.5f);
- endValuePosition = startValuePosition;
- endValueRotation = startValueRotation;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- startValuePosition = _mainCamera.Position;
- startValueRotation = _mainCamera.Rotation;
- }
- else if(_internalCameraPosition == CameraPosition.Interior)
- {
- RepositionFor((Vehicle)_target);
- }
- }
- break;
- case CameraPosition.Wheels:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- if (_internalCameraPosition != CameraPosition.Car)
- RepositionFor((Vehicle)_target);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -60f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 510f,
- RightHorizontalValue = _target.Heading - 380f,
- };
- _cameraZoom = 4f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _target.Position - _target.RightVector * 4f + _target.UpVector;
- endValueRotation = new Vector3(0, 0, _target.Heading-90f);
- }
- break;
- case CameraPosition.Interior:
- {
- IsLerping = false;
- var headPos = Game.Player.Character.GetBoneCoord(Bone.IK_Head);
- World.DestroyAllCameras();
- _mainCamera = World.CreateCamera(headPos + new Vector3(0, 0, 0.1f),new Vector3(0,0,_target.Heading), GameplayCamera.FieldOfView);
- World.RenderingCamera = _mainCamera;
- _targetPos = headPos;
- RotationMode = CameraRotationMode.FirstPerson;
- Game.Player.Character.Alpha = 0;
- CameraClamp = new CameraClamp() { MaxVerticalValue = -60f, MinVerticalValue = -3f };
- _justSwitched = true;
- }
- break;
- case CameraPosition.Engine:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "engine");
- _cameraZoom = 3f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector*3f + _target.UpVector;
- endValueRotation = new Vector3(0, 0, -_target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 250.6141f,
- RightHorizontalValue = _target.Heading - 470.79f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.Trunk:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "boot");
- _cameraZoom = 3f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * -3f + _target.UpVector;
- endValueRotation = new Vector3(0, 0, _target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 410f,
- RightHorizontalValue = _target.Heading - 300f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.FrontBumper:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "neon_f");
- _cameraZoom = 2f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * 2f + _target.UpVector;
- endValueRotation = new Vector3(0, 0, -_target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 250.6141f,
- RightHorizontalValue = _target.Heading - 470.79f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.Grille:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "neon_f");
- _cameraZoom = 2f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * 2f + _target.UpVector*3f;
- endValueRotation = new Vector3(0, 0, -_target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 250.6141f,
- RightHorizontalValue = _target.Heading - 470.79f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.RearBumper:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "neon_b");
- _cameraZoom = 2f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * -2f + _target.UpVector;
- endValueRotation = new Vector3(0, 0, _target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 410f,
- RightHorizontalValue = _target.Heading - 300f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.Tank:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "neon_b");
- _cameraZoom = 2f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector*-2f;
- endValueRotation = new Vector3(0, 0, _target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 410f,
- RightHorizontalValue = _target.Heading - 300f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.Plaque:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- switch (_target.Model.Hash)
- {
- case -1013450936:
- case -1361687965:
- _targetPos = GetBonePosition(_target, 28);
- break;
- case -1790546981:
- _targetPos = GetBonePosition(_target, 30);
- break;
- case -2040426790:
- _targetPos = GetBonePosition(_target, 60);
- break;
- case 1896491931:
- _targetPos = GetBonePosition(_target, 33);
- break;
- case 2006667053:
- _targetPos = GetBonePosition(_target, 41);
- break;
- }
- _cameraZoom = 0.5f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * -0.5f + _target.UpVector*0.1f;
- var tRot = _target.Heading;
- if (tRot > 180f)
- tRot -= 360f;
- endValueRotation = new Vector3(0, 0, tRot);
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 410f,
- RightHorizontalValue = _target.Heading - 300f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.BackPlate:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "platelight");
- _cameraZoom = 1f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * -1f + _target.UpVector;
- endValueRotation = new Vector3(0, 0, _target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 410f,
- RightHorizontalValue = _target.Heading - 300f,
- };
- _justSwitched = true;
- }
- break;
- case CameraPosition.FrontPlate:
- {
- Game.Player.Character.Alpha = 255;
- RotationMode = CameraRotationMode.Around;
- _targetPos = GetBonePosition(_target, "neon_f");
- _cameraZoom = 1f;
- startValueRotation = _mainCamera.Rotation;
- startValuePosition = _mainCamera.Position;
- duration = 1000f;
- IsLerping = true;
- startTime = DateTime.Now;
- endValuePosition = _targetPos + _target.ForwardVector * 2f + _target.UpVector*2f;
- endValueRotation = new Vector3(0, 0, -_target.Heading);
- _mainCamera.StopPointing();
- _mainCamera.PointAt(_targetPos);
- CameraClamp = new CameraClamp()
- {
- MaxVerticalValue = -40f,
- MinVerticalValue = -3f,
- LeftHorizontalValue = _target.Heading - 250.6141f,
- RightHorizontalValue = _target.Heading - 470.79f,
- };
- _justSwitched = true;
- }
- break;
- }
- }
- public WorkshopCamera()
- {
- World.DestroyAllCameras();
- }
- public void Stop()
- {
- World.RenderingCamera = null;
- World.DestroyAllCameras();
- }
- public void RepositionFor(Vehicle lowrider)
- {
- World.DestroyAllCameras();
- _mainCamera = World.CreateCamera(lowrider.Position - lowrider.ForwardVector*5f + new Vector3(0f, 0f, 1.5f), CutsceneManager.DirectionToRotation(lowrider.ForwardVector*-5f),
- GameplayCamera.FieldOfView);
- _mainCamera.PointAt(lowrider);
- World.RenderingCamera = _mainCamera;
- _target = lowrider;
- _targetPos = lowrider.Position;
- _cameraZoom = 5f;
- _internalCameraPosition = CameraPosition.Car;
- RotationMode = CameraRotationMode.Around;
- CameraClamp = new CameraClamp() {MaxVerticalValue = -40f, MinVerticalValue = -3f};
- _mainCamera.Shake(CameraShake.Hand, 0.5f);
- }
- public bool IsMouseInMenu()
- {
- var safe = UIMenu.GetSafezoneBounds();
- return UIMenu.IsMouseInBounds(new Point(safe.X, safe.Y), new Size(431, 107 + 37 + (38*10) + 18 + 18));
- }
- private bool _justSwitched;
- public void Update()
- {
- if (_mainCamera == null) return;
- Game.DisableControl(0, Control.VehicleMouseControlOverride);
- if (IsLerping)
- {
- var t = DateTime.Now;
- if (t.Subtract(startTime).TotalMilliseconds > duration)
- {
- IsLerping = false;
- _mainCamera.Position = endValuePosition;
- _mainCamera.Rotation = endValueRotation;
- return;
- }
- _mainCamera.Position = LerpVector((float)t.Subtract(startTime).TotalMilliseconds, duration, startValuePosition, endValuePosition);
- _mainCamera.Rotation = LerpVector((float)t.Subtract(startTime).TotalMilliseconds, duration, startValueRotation, endValueRotation);
- return;
- }
- if (_justSwitched)
- {
- _justSwitched = false;
- return;
- }
- if (Game.IsControlJustPressed(0, Control.Attack) && !_isDragging && !IsMouseInMenu())
- {
- _isDragging = true;
- var mouseX = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int)Control.CursorX);
- var mouseY = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int)Control.CursorY);
- Function.Call((Hash)0x8DB8CFFD58B62552, 4);
- mouseX = (mouseX * 2) - 1;
- mouseY = (mouseY * 2) - 1;
- _dragOffset = new PointF(mouseX, mouseY);
- }
- if (Game.IsControlJustReleased(0, Control.Attack) && _isDragging)
- {
- _isDragging = false;
- _dragOffset = new Point();
- Function.Call((Hash)0x8DB8CFFD58B62552, 0);
- }
- if (RotationMode == CameraRotationMode.Around)
- {
- if (_isDragging)
- {
- Function.Call(Hash._SHOW_CURSOR_THIS_FRAME);
- var dir = CutsceneManager.RotationToDirection(_mainCamera.Rotation);
- var len = (_targetPos - _mainCamera.Position).Length();
- var rotLeft = _mainCamera.Rotation + new Vector3(0, 0, -10);
- var rotRight = _mainCamera.Rotation + new Vector3(0, 0, 10);
- var right = CutsceneManager.RotationToDirection(rotRight) -
- CutsceneManager.RotationToDirection(rotLeft);
- var rotUp = _mainCamera.Rotation + new Vector3(-20, 0, 0);
- var rotDown = _mainCamera.Rotation + new Vector3(20, 0, 0);
- var up = CutsceneManager.RotationToDirection(rotUp) - CutsceneManager.RotationToDirection(rotDown);
- var mouseX = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int) Control.CursorX);
- var mouseY = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int) Control.CursorY);
- mouseX = (mouseX*2) - 1;
- mouseY = (mouseY*2) - 1;
- Vector3 rotation = new Vector3();
- if(!IsCameraClamped(true, mouseX - _dragOffset.X))
- rotation += right*15*(mouseX - _dragOffset.X);
- if (!IsCameraClamped(false, mouseY - _dragOffset.Y))
- rotation += up*-((mouseY - _dragOffset.Y)*15);
- rotation += dir*(len - CameraZoom);
- _mainCamera.Position += rotation;
- _dragOffset = new PointF(mouseX, mouseY);
- }
- if (Game.CurrentInputMode == InputMode.GamePad)
- {
- var dir = CutsceneManager.RotationToDirection(_mainCamera.Rotation);
- var len = (_targetPos - _mainCamera.Position).Length();
- var rotLeft = _mainCamera.Rotation + new Vector3(0, 0, -10);
- var rotRight = _mainCamera.Rotation + new Vector3(0, 0, 10);
- var right = CutsceneManager.RotationToDirection(rotRight) -
- CutsceneManager.RotationToDirection(rotLeft);
- var rotUp = _mainCamera.Rotation + new Vector3(-20, 0, 0);
- var rotDown = _mainCamera.Rotation + new Vector3(20, 0, 0);
- var up = CutsceneManager.RotationToDirection(rotUp) - CutsceneManager.RotationToDirection(rotDown);
- var mouseX = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int) Control.LookLeftRight);
- var mouseY = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int) Control.LookUpDown);
- Vector3 rotation = new Vector3();
- if(!IsCameraClamped(true, mouseX))
- rotation += right*mouseX*0.6f;
- if (!IsCameraClamped(false, mouseY))
- rotation += up*-mouseY*0.5f;
- rotation += dir*(len - CameraZoom);
- _mainCamera.Position += rotation;
- }
- }
- else if(RotationMode == CameraRotationMode.FirstPerson)
- {
- if (_isDragging)
- {
- Function.Call(Hash._SHOW_CURSOR_THIS_FRAME);
- var mouseX = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int)Control.CursorX);
- var mouseY = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int)Control.CursorY);
- mouseX = (mouseX * 2) - 1;
- mouseY = (mouseY * 2) - 1;
- mouseY *= -1;
- var right = new Vector3(0, 0, 1);
- var up = new Vector3(1, 0, 0);
- Vector3 rotation = new Vector3();
- if (!IsCameraClamped(true, mouseX - _dragOffset.X))
- rotation += right * 20 * (mouseX - _dragOffset.X);
- if (!IsCameraClamped(false, mouseY - _dragOffset.Y))
- rotation += up * -((mouseY - _dragOffset.Y) * 20);
- _mainCamera.Rotation += rotation;
- _dragOffset = new PointF(mouseX, mouseY);
- }
- if (Game.CurrentInputMode == InputMode.GamePad)
- {
- var mouseX = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int)Control.LookLeftRight);
- var mouseY = Function.Call<float>(Hash.GET_CONTROL_NORMAL, 0, (int)Control.LookUpDown);
- mouseX *= -1;
- var right = new Vector3(0, 0, 1);
- var up = new Vector3(1, 0, 0);
- Vector3 rotation = new Vector3();
- if (!IsCameraClamped(true, mouseX))
- rotation += right * mouseX * 4f;
- if (!IsCameraClamped(false, mouseY))
- rotation += up * -mouseY * 4f;
- _mainCamera.Rotation += rotation;
- }
- }
- }
- public bool IsCameraClamped(bool horizontally, float delta)
- {
- if (horizontally)
- {
- var goingLeft = delta < 0;
- if (goingLeft && !CameraClamp.LeftHorizontalValue.HasValue)
- return false;
- if (!goingLeft && !CameraClamp.RightHorizontalValue.HasValue)
- return false;
- if (CameraClamp.LeftHorizontalValue > 180f)
- CameraClamp.LeftHorizontalValue = CameraClamp.LeftHorizontalValue - (360*((int)(CameraClamp.LeftHorizontalValue/360))+1);
- if (CameraClamp.RightHorizontalValue > 180f)
- CameraClamp.RightHorizontalValue = CameraClamp.RightHorizontalValue - (360 * ((int)(CameraClamp.RightHorizontalValue / 360)) + 1);
- var sameHemisphereLeft = (_mainCamera.Rotation.Z > 0f && CameraClamp.LeftHorizontalValue > 0f) ||
- (_mainCamera.Rotation.Z < 0f && CameraClamp.LeftHorizontalValue < 0f);
- var sameHemisphereRight = (_mainCamera.Rotation.Z > 0f && CameraClamp.RightHorizontalValue > 0f) ||
- (_mainCamera.Rotation.Z < 0f && CameraClamp.RightHorizontalValue < 0f);
- if (goingLeft && _mainCamera.Rotation.Z > CameraClamp.RightHorizontalValue && sameHemisphereRight)
- return true;
- if (!goingLeft && _mainCamera.Rotation.Z < CameraClamp.LeftHorizontalValue && sameHemisphereLeft)
- return true;
- return false;
- }
- else
- {
- var goingDown = delta < 0;
- if (goingDown && !CameraClamp.MinVerticalValue.HasValue)
- return false;
- if (!goingDown && !CameraClamp.MaxVerticalValue.HasValue)
- return false;
- if (goingDown && _mainCamera.Rotation.X > CameraClamp.MinVerticalValue)
- return true;
- if (!goingDown && _mainCamera.Rotation.X < CameraClamp.MaxVerticalValue)
- return true;
- return false;
- }
- }
- public static float Clamp(float value, float min, float max)
- {
- if (value > max) return max;
- if (value < min) return min;
- return value;
- }
- public static Vector3 GetBonePosition(Entity target, string bone)
- {
- return Function.Call<Vector3>((Hash) 0x44A8FCB8ED227738, target.Handle, Function.Call<int>((Hash) 0xFB71170B7E76ACBA, target.Handle, bone));
- }
- public static Vector3 GetBonePosition(Entity target, int bone)
- {
- return Function.Call<Vector3>((Hash)0x44A8FCB8ED227738, target.Handle, bone);
- }
- public static float QuadraticEasing(float currentTime, float startValue, float changeInValue, float duration)
- {
- currentTime /= duration/2;
- if (currentTime < 1) return changeInValue/2*currentTime*currentTime + startValue;
- currentTime--;
- return -changeInValue/2*(currentTime*(currentTime - 2) - 1) + startValue;
- }
- public static Vector3 LerpVector(float currentTime, float duration, Vector3 startValue, Vector3 destination)
- {
- var output = new Vector3();
- output.X = QuadraticEasing(currentTime, startValue.X, destination.X - startValue.X, duration);
- output.Y = QuadraticEasing(currentTime, startValue.Y, destination.Y - startValue.Y, duration);
- output.Z = QuadraticEasing(currentTime, startValue.Z, destination.Z - startValue.Z, duration);
- return output;
- }
- private float _cameraZoom;
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement