Say I had a part (A) that has a LookVector of -0, -0, 1 and another part (B) that had a LookVector of -0, -0, -1, how would I make a part (A) have a LookVector assigned that is 50% (or any other number) of what the LookVector of Part (B) is (with respect to Part A’s original LookVector)?
Here’s my code, it uses Non-Humanoid characters so I have to be specific with the maths, I had a previous implementation that would work, however when a high attackWalkspeed was implemented it would completely bug out and teleport the serverPart to non existent position. This is run constantly in a PreSimulation.
function regular_zombie:walkingLogic(dt:number, moveToPosition:Vector3, distance: number)
local partWalkingParamas: RaycastParams = self._cModules.logic:createPartWalkingParams(self.instance)
local partWalkingRaycast: RaycastResult = self._cModules.logic:partWalkingRaycast(
partWalkingParamas,
self.serverPart.Position
)
local direction: Vector3
local part: Part = self._cModules.logic:getColliding(self.collidingParams, self.serverPart)
if not part then -- zombie free to move to position
direction = (moveToPosition - self.serverPart.Position).Unit * Vector3.new(1,0,1)
end
if part then
direction = (self.serverPart.Position - part.Position).Unit * Vector3.new(1,0,1)
end
local _walkToPosition: Vector3
local _lookAtDirection: Vector3
local _finalCFrame: CFrame
-- if not attackign walking normally
if self.currentAttackingMove == '' and not self.isAttacking then
_walkToPosition = self.serverPart.Position + (direction * (self.walkspeed*dt))
_lookAtDirection = Vector3.new(
moveToPosition.X,
self.serverPart.Position.Y,
moveToPosition.Z
)
end
-- if attacking then change walkspeed to that of the moves attackspede
if self.currentAttackingMove ~= '' and self.ATTACKS[self.currentAttackingMove].canMove then
local attackWalkspeed: number = self.ATTACKS[self.currentAttackingMove].walkspeed
local rotation: number = self.ATTACKS[self.currentAttackingMove].rotation
_walkToPosition = self.serverPart.Position + (direction * (attackWalkspeed*dt)) * Vector3.new(1,0,1)
-- if move has property of rotation then slowly rotate that mob according to the rotation speed
if rotation and rotation > 0 then
----///////////////////////////////////////////////
----///////////////////////////////////////////////
----///////////////////////////////////////////////
-- HERE, the previous code I put would often bug out when the attackWalkspeed was too high
--[[local targetDirection = (Vector3.new(moveToPosition.X, self.serverPart.Position.Y, moveToPosition.Z) - self.serverPart.Position).Unit
local currenDirection = self.serverPart.CFrame.LookVector
local rotationalStep = math.min(.1, rotation*dt)
local newDirection = currenDirection:Lerp(targetDirection, rotationalStep)
_walkToPosition = distance < self.M_CONSTANTS.IDLE_THRESHOLD and self.serverPart.Position or self.serverPart.Position + (newDirection * (attackWalkspeed*dt))*Vector3.new(1,0,1)
_lookAtDirection = (self.serverPart.Position + newDirection)--]]
elseif not rotation then
_lookAtDirection = Vector3.new(
moveToPosition.X,
self.serverPart.Position.Y,
moveToPosition.Z
)
elseif rotation <= 0 then
_lookAtDirection = Vector3.new(
self.serverPart.Position.X,
self.serverPart.Position.Y,
self.serverPart.Position.Z
)
end
end
if partWalkingRaycast then -- make it so when they walk on a PART they will adjust their Y position to that
_walkToPosition = Vector3.new(
_walkToPosition.X,
(partWalkingRaycast.Instance.Size.Y/2 + partWalkingRaycast.Instance.Position.Y) + 8.5, -- change this number for everr mob size
_walkToPosition.Z
)
end
if not self.isWalking and not self.isAttacking then
_finalCFrame = CFrame.new(
self.serverPart.Position,
_lookAtDirection
)
else
_finalCFrame = CFrame.new(
_walkToPosition,
_lookAtDirection
)
end
self.serverPart.CFrame = _finalCFrame
end