Scripting Helpers is winding down operations and is now read-only. More info→
Ad
Log in to vote
0

Making a part face the direction of a vector?

Asked by
0te 35
4 years ago

Hello, I've managed to get as far as making the code below to get the direction vector that the player is moving:

while wait(0.2) do
    if root.Velocity.Magnitude == 0 then
        direction = root.Velocity
    else
        direction = root.Velocity.Unit
    end

    -- applying the direction vector to the part

    print(direction)


end

However, I have a part welded to the character's humanoid root part that I want to constantly rotate to face this direction vector. I'm not sure how I would go about doing this. The only concept I can think of is trying to get some sort of vector from the part and setting it to the direction vector then maybe using dot product to verify that the two lines are parallel or maybe I'm talking complete bollocks.

This may not be the most efficient way to do it, however I'm still in the process of learning the language and am open to any concepts and methods you may have.

Any form of help is greatly appreciated.

1 answer

Log in to vote
0
Answered by
TGazza 1336 Moderation Voter
4 years ago
Edited 4 years ago

Since you said your welding your part to the player via the root part of the humanoid you can't use the velocity like for instance if the player was stationary the Vector3.unit would be dividing by zero so you're positioning Vector will return NAN or not a number. to get around this problem you could record the position of your part each tick then save the previous position to get the direction from subtracting one from the other and if we're not moving use the lookvector of the root part as reference.

Something like:

local root = script.Parent
local Pos = root.Position
local OldPos = Pos -- just a way to record the previous position. its best to update this at the last thing in your loop, see below!

-- a debug brick for debugging 
local DBug_Part = (function()
    local P = Instance.new("Part",workspace)
    P.Anchored = true
    P.Size = Vector3.new(1,1,1)
    return P
end)()
while true do

    Pos = root.Position
    local DeltaPos = (Pos - OldPos)

    -- check to see if (Pos - OldPos).magnitude isnt 0 if it is set the direction to the root.CFrame.LookVector if it not then set it to the unit of those two vector3
    direction  = DeltaPos.magnitude ~= 0 and DeltaPos.unit or root.CFrame.LookVector

    DBug_Part.Position = Pos + (direction *2)
    -- applying the direction vector to the part

    print(direction)

    OldPos = Pos
    wait(0.2) -- most important bit we need the wait before the loop restarts to get the offset between Pos and OldPos otherwise it would return NAN or a magnitude of 0
end

a Much nicer way to make sure your part 'Remembers' which way it was pointing is to change the above code to the following:

local root = script.Parent
local Pos = root.Position
local OldPos = Pos
local OldDir = Vector3.new() -- Remember the last direction we had!

local DBug_Part = (function()
    local P = Instance.new("Part",workspace)
    P.Anchored = true
    P.Size = Vector3.new(1,1,1)
    P.CanCollide = false
    return P
end)()
while true do

    Pos = root.Position
    local DeltaPos = (Pos - OldPos)


    direction  = DeltaPos.magnitude ~= 0 and DeltaPos.unit or OldDir -- this is changed to the previous Dir Change if we're not moving!

    DBug_Part.Position = Pos + (direction *2)
    -- applying the direction vector to the part

    --print(direction)

    OldPos = Pos
    OldDir = direction
    wait()
end

Kinda related to this but I've made a little example from the above code that moves a part in a sine wave in 3 directions and positions a part in the direction the part is travelling. Both parts are anchored!

Code: (your free to use this code however you want. I just threw it together lol

local root = script.Parent

local Pos = root.Position
local OldPos = Pos
local OldDir = Vector3.new()
local OffsetPos = root.Position
local DBug_Part = (function()
    local P = Instance.new("Part",workspace)
    P.Anchored = true
    P.Size = Vector3.new(1,1,1)
    P.CanCollide = false

    return P
end)()

local tx = 0
local ty = 0
local tz = 0
root.FrontSurface = Enum.SurfaceType.Hinge
while true do


    local ax = tx * math.pi/180
    local ay = ty * math.pi/90
    local az = tz * math.pi/45

    local X = 10 * math.cos(ax)
    local Y = 10 * math.sin(ay)
    local Z = 10 * math.sin(az)


    root.CFrame = CFrame.new(OffsetPos+Vector3.new(X,Y,Z), Pos)*CFrame.Angles(0,math.rad(180),0)
    Pos = root.Position
    local DeltaPos = (Pos - OldPos)


    direction  = DeltaPos.magnitude ~= 0 and DeltaPos.unit or OldDir

    DBug_Part.Position = Pos + (direction *3)
    -- applying the direction vector to the part

    --print(direction)

    OldPos = Pos
    OldDir = direction
    wait()
    tx = tx+0.5
    ty = ty+0.7
    tz = tz+0.2
end
0
That's great. I'm still going over it to make sure I understand it fully. Thank you for taking the time to explain it in such depth. 0te 35 — 4y
0
your welcome mate! :) TGazza 1336 — 4y
Ad

Answer this question