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

May someone explain each line of this script especially the math parts?

Asked by 9 years ago

I especially needed understand with the 3 last main lines ----> CFrame.Angles(math.pi/2,0,0);--rotate it so that the hand points that way weld.C0=CFrame.new();--set C0 to identity matrix so it is out of the equation weld.C1=desired_p1:inverse()*weld.Part0.CFrame;--same equation as shown above

local playa=game.Players.LocalPlayer;

script.Parent.Selected:connect(function(mouse)
    while Wait() do
    local weld=playa.Character.Torso["Left Shoulder"];
    --[[
        p0=part0.CFrame
        c0=c0
        p1=part1.CFrame
        c1=c1

        p1*c1 == p0*c0
        c1 == p1:inverse()*p0*c0
        c0 == p0:inverse()*p1*c1
    --]]
    local desired_p1=CFrame.new(--the CFrame that we want the arm to be at
                (weld.Part0.CFrame*CFrame.new(-1,1,0)).p,--the position we want
                mouse.hit.p--look at the mouse
            )*
            CFrame.Angles(math.pi/2,0,0);--rotate it so that the hand points that way
    weld.C0=CFrame.new();--set C0 to identity matrix so it is out of the equation
    weld.C1=desired_p1:inverse()*weld.Part0.CFrame;--same equation as shown above
end end
)

1 answer

Log in to vote
10
Answered by
BlueTaslem 18071 Moderation Voter Administrator Community Moderator Super Administrator
9 years ago

How CFrames Work

CFrames are position and orientation together. They are implemented as matrices, and thus have the properties of matrix addition, product, and inverse.

World Space

When you get the .CFrame of a part, that is in world space -- it's relative to the world as a whole. Thus (0, 0, 0) is in the middle of the world, and (0, 1, 0) is up, etc.

Object Space

You can instead imagine your position and orientation relative to another CFrame. For instance, the top surface of a part in its object space will always be (0, 1, 0) no matter how the part is tilted.

You can convert between Object Space and World Space using object:toWorldSpace(objectSpaceCFrame) and object:toObjectSpace(worldSpaceCFrame).

For example, you can use :toObjectSpace to find the distance between two parts:

local BRelativeToA = A.CFrame:toObjectSpace( B.CFrame )
print( BRelativeToA.p.magnitude ) -- distance between A and B

:toObjectSpace will "undo" :toWorldSpace and vice versa.

Multiplication

If A and B are CFrames, then A * B means "B, but relative to A" -- A * B is the same thing as A:toWorldSpace(B). This is exactly a matrix product.

Example

local up = CFrame.new(0, 5, 0)
local part = workspace.Part.CFrame

local out = part * up -- the top of the part

Inverse

A:inverse() * B is exactly the same thing as A:toObjectSpace(B). Again, this corresponds exactly to the matrix inverse.

Your Script

weld.Part0.CFrame*CFrame.new(-1,1,0)

This will be 1 stud left and one stud up of the first part in the weld. If you imagine the part 2x2x2 cube, it will be one of the corners.

CFrame.new( ... , mouse.Hit.p )

CFrame.new(from, to) makes a CFrame positioned at from and looking towards to. This means we get a point looking from the point described above towards where the mouse is pointing.

* CFrame.Angles(math.pi/2,0,0);

This rotates the CFrame in place, tilting it 90 degrees down about it's X axis -- the 'front' is now facing down instead of forward.

Welds

Welds have a C0 and C1 which are Object Space to some arbitrary point in space. Usually it's easier to just have one part relative to the other, so you want one of them to be the same as that object space.

That is when you have C0 (or C1) as the default CFrame -- CFrame.new().

desired_p1:inverse()*weld.Part0.CFrame

This lets us get a CFrame in the object space of the weld -- it's relative to where Part0 is, (from the previous step) is also where our weld is.

However, I think it ought to be the other way around, probably the rest of it was made to work with this order.

This effectively let's you use World-Space up until the final point when you want to put it into the weld, which makes it very easy to manage.

0
So if I were to use toworldspace i can measure a part's distance from (0,0,0)...? Blockeus 68 — 9y
0
CFrame.new():toObjectSpace( blah ) would do that, but that's unnecessary, since CFrame.new():toObjectSpace(blah) is the same thing as blah -- since "world space" is really essentially 'object space' for the origin BlueTaslem 18071 — 9y
0
OH to world space pretends that a object is the origin its self? Blockeus 68 — 9y
0
OH to world space pretends that a object is the origin its self? Blockeus 68 — 9y
View all comments (6 more)
0
Yes BlueTaslem 18071 — 9y
0
One more thing can you tell me how toobjectspace works in really simple terms... like can you dumb it down to the point where I'm like alittle kid. Blockeus 68 — 9y
0
tooObjectSpace compares the CFrame of a part to another part instead of a part to the world, so if you have one part at 0,5,0 world space and another part at 0,10,0 at world space, then you called diff = Part2:toObjectSpace(Part1) it should return 5 since part1 is the origin and part 2 is 5 studs above it, it will also calculate rotation for you I believe dragonkeeper467 453 — 9y
0
It's position + orientation relative to another position + orientation. E.g., my right shoulder is always in the same 'place' relative to my stomach -- that constant is torso:toObjectSpace(shoulder) BlueTaslem 18071 — 9y
0
One more thing-I'm still confused with the purpose of CFrame.new(); Blockeus 68 — 9y
0
CFrame.new() is a "blank" CFrame. It's at the origin with the default orientation. BlueTaslem 18071 — 9y
Ad

Answer this question