My jet won't stop spinning. Problems with CFrame

Hello fellow developers! For my latest project I’ve decided to try to tackle making a jet! I’m about an hour in and I think I’ve made good progress. I do however have a problem with my current control system. When the player aims their jet directly up into the sky or straight down the jet starts spinning out of control! The video below shows my problem:

https://i.gyazo.com/653d0afd29d76e19d1f54aff9032b823.mp4

Here is the client script located in StarterGui:

local RS = game:GetService("RunService")

local plr = game.Players.LocalPlayer
repeat wait() until plr.Character
local char = plr.Character
local mouse = plr:GetMouse()

local jet = game.Workspace.Jet

mouse.TargetFilter = jet


local camera = game.Workspace:WaitForChild("Camera")

local cameraOffset = Vector3.new(0, 8, 20)

RS.RenderStepped:Connect(function()
	if jet.VehicleSeat.Occupant and jet.VehicleSeat.Occupant.Parent and jet.VehicleSeat.Occupant.Parent == char then
		camera.CameraType = Enum.CameraType.Scriptable
		camera.CFrame = camera.CFrame:Lerp(jet.CFrame * CFrame.new(cameraOffset), 0.1) 

		print(((jet.Configuration.MaxSpeed.Value - jet.Speed.Value) / jet.Configuration.MaxSpeed.Value) * 0.8 + 0.1)
		jet.CFrame = jet.CFrame:Lerp(CFrame.lookAt(jet.Position, mouse.Hit.p), ((jet.Configuration.MaxSpeed.Value - jet.Speed.Value) / jet.Configuration.MaxSpeed.Value) * 0.8 + 0.1)
	end
end)

And here is the server script located inside the jet part:

local MaxSpeed = script.Parent.Configuration.MaxSpeed.Value

local speed = 0

while wait(0.01) do
	if script.Parent.VehicleSeat.Occupant then
		if script.Parent.VehicleSeat.Throttle == 1 and speed < 100 then
			speed += 1
		elseif script.Parent.VehicleSeat.Throttle == -1 and speed > 1 then
			speed -= 1
		end
		
		script.Parent.Speed.Value = speed / 100 * MaxSpeed

		script.Parent.LinearVelocity.VectorVelocity = Vector3.new(speed / 100 * MaxSpeed, speed / 100 * MaxSpeed, speed / 100 * MaxSpeed) * script.Parent.CFrame.LookVector
	end
end

Any ideas on how this could be fixed would be very much appreciated. :smile: :small_airplane:

Edit:

Please ignore the jittering in the plane. I will be trying to fix that in the meantime

2 Likes

Are you sure that the issue isn’t caused by having your cursor off-centre? If so, there isn’t really a whole lot you can do, unless you set a deadzone on the cursor which would be annoying to implement

3 Likes

I don’t believe it’s off-centred. How would I check for that?

1 Like

I mean off-centre on the screen - not lined up perfectly with the middle of the screen.

this is an issue found in basically all mouse-controlled steering systems.

2 Likes

Well at the moment I’m pointing the jet at the player’s mouse hit position
but now that I think about it, using the mouse X and Y position might work better!

1 Like

Hey, exactly i just made like same jet and tested it on gamepad, yeah it mouse steer problem, on gamepad it won’t spin.

1 Like

That’s interesting! Well I’ll try using the mouse screen coords instead and see how that does

This is happening because the camera is being positioned in such a way that the mouse will constantly control it. You can do either of these to solve the problem:

  1. Edit the camera.
  2. Set the mouse to LockCenter and use UserInputService to find mouse delta (Recommended).

I would recommend the 2nd option as it allows you to keep your current camera system which I think is necessary.

1 Like

Thank you for the help! I actually managed to figure it out in the end. I’ll send my solution below.

1 Like

In the end I decided to use the Mouse.X and mouse.Y values instead of the Mouse world position. This means that you can now do loops in the sky without the spinning occuring!

Here is my solution:

jet.CFrame = jet.CFrame:Lerp(jet.CFrame * CFrame.Angles(math.rad((mouse.Y - screenCentre.Y) / screenCentre.Y * -turnSpeed), math.rad((mouse.X - screenCentre.X) / screenCentre.X * -turnSpeed), 0), 0.1)

Thank you everyone who gave their own solutions! Although your solutions were slightly different you did give me the idea to try this instead! :smiley:

You can check out the working version here:

https://i.gyazo.com/1578e9ee539bd62dfb1fd105ad55c199.mp4

1 Like

That’s cool, but I would’ve kept using UserInputService for mouse position (mostly because Mouse is basically deprecated now and was a relic from 2007)

Anyways, to get the screen size, what did you do? I would use workspace.CurrentCamera.ViewportSize, but if you did anything different, let me know.

Oh that’s good to know! From now on I’ll try to use UIS then. That’s basically what I used. In absolute honesty I grabbed some code from someone else’s devforum post but it seemed understandable to me.