
Important Links
Roblox Store: Motion Roblox Store
Discord Development Server: Motion Development
What’s New in v1.5.0
- Ghost Onions
- Markers and Connecting Callbacks on Markers hit
MySequence:LinkMarkerAction("Explosion", function()
-- anything here
end)
- MGizmos (New Gizmo System)
v1.5.0 Introduces a completely new gizmo system, that is more reliable, smoother, and better overall. - Instance Binding
Sequences (animations) can now be bound dynamically to instances at runtime.
MySequence:BindInstance(TargetInstance, InstanceMotionID)
MySequence:Play()
This allows a single sequence to be reused across multiple objects without duplication.
- Editor Enhancements
- Cleaner timeline interactions
- Improved track and channel handling
- Better visual separation of lanes
- General UX polish across the editor
What is Motion?
Motion isn’t a traditional animation editor.
It’s a timeline based Motion system designed for animating anything over time — parts, cameras, rigs, and properties with direct runtime control.
While most Roblox animation tools focus on character rigs and predefined animation formats, Motion treats animation as data. Every sequence is authored on a real timeline, previewed in Studio, and exported as raw Luau data for high-performance in-game playback.
Roadmap [ +1.5.0 ]
- IK & constraint-based controls
- Importing Keyframe Sequences & Motion Sequences
- Further gizmo improvements
- String property animation
- Editor performance optimizations
- Public documentation & examples
Complete List of shortcuts
to make the process of creating animations within Motion faster, I recommend using the shortcuts via Files > Customize Shortcuts
-- The complete shortcuts for v1.5.0
local Actions = {
["Play_Sequence"] = plugin:CreatePluginAction("Motion_PlaySeq", "Play a sequence", "Default: Space", "", true),
["Delete_Keyframe"] = plugin:CreatePluginAction("Motion_DeleteKeyFrame", "Delete a Keyframe", "Default: X", "", true),
["Create_KeyFrame"] = plugin:CreatePluginAction("Motion_CreateKeyFrame", "Creates a keyframe", "Default: I", "", true),
["To_Start"] = plugin:CreatePluginAction("Motion_ToStart", "Return to 0s", "Default: 0", "", true),
["Undo"] = plugin:CreatePluginAction("Motion_Undo", "Undo an action via history", "Default: Ctrl+Shift+Z", "", true),
["Redo"] = plugin:CreatePluginAction("Motion_Redo", "Redo an action via history", "Default: Ctrl+Shift+Y", "", true),
["Insert_Marker"] = plugin:CreatePluginAction("Motion_InsertMarker", "Insert a marker at current time", "Default: M", "", true),
["Toggle_OnionSkin"] = plugin:CreatePluginAction("Motion_OnionSkin", "Toggle Onion Skin", "Default: LCtrl + R", "", true),
}
Motion is completely free at the moment, you can try it out now!
What makes Motion special to you?
- Runtime engine
- Curve Editor
- UI/UX
- Flexibility
Developer API
If you want to control your sequences via script, use the Motion Runtime Engine.
View Full API Documentation
Initialization
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
Playing a Sequence
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:Play()
Stopping a Sequence
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:Play()
task.wait(2) -- a bit of delay
MySequence:Stop()
Pausing a Sequence
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:Play()
task.wait(2)
MySequence:Pause()
Seeking (Rendering value at a specific time in a sequence)
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:Seek(3) -- Applies all animations at the third second without playing
Checking if a sequence is completed
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:Play()
MySequence.Completed:Connect(function()
print("Completed!")
end)
Checking if a sequence is stopped
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:Play()
--optionally: stop it to check
MySequence:Stop()
MySequence.Stopped:Connect(function()
print("Completed!")
end)
Binding an Instance
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:BindInstance(game.player.LocalPlayer.Character, nil) -- NOTE: 2nd parameter can not be set to nil, you must get the ID from the Motion sequence Module and paste it here
-- Also binding must happen before playing the sequence
MySequence:Play()
Linking a callback to a Marker
local Motion = require(game.ReplicatedStorage.Motion.Engine)
local Data = require(game.ReplicatedStorage.MySequence)
local MySequence = Motion.new(Data)
MySequence:LinkMarkerAction("KillPlayer", function()
-- logic goes here
end)
--Also linking an action to marker must happen before playing the sequence
MySequence:Play()
Advanced Features & Tips
Director Track
Director track is a special track that is generated automatically every project. Director Track is the track that controls the camera. You can create clips inside unlike normal tracks which are keyframe-based.
The Director Track has two properties fields Field Of View, and Roll, you can create keyframes and animate those normally.
To create a clip:
- Select the object you want to act as the camera, and hit the “+” button beside the director track
- By clicking on the clip, you can resize it by dragging the edges, and as well moving it by also dragging it.
IMPORTANT: Director track keyframes are relative to the clips, meaning when the runtime engine renders them, they will be rendered in relative time not global time. e.g., clip starts at 5s and ends 10s, and you have a keyframe at 5s, the keyframe is actually handles as if it’s at 1s because the start of the clip is at 1s, and so it will only render when its 5s
- The Eye Icon (toggleable) is for when you want to move your camera while animating, because when you play a sequence with director clips your camera is fixed at the object you created the clip with.
Curve Editor
The curve editor let’s you analyze and interact with numeric functions represented on a graph. This makes super amazing and cinematic when it you actually pair bezier curve interpolation along side it.
How to access the curve editor?
To access the curve editor you have two options:
- Hovering over View > Graph Editor
- Clicking the curved line icon along side the "+ Track+ button on the sidebar

After loading the curve editor, you should see something like this:
Currently it’s empty because we have no real Motion Animation Tracks, So let’s add one.
I added a part as Motion Animation Track and added CFrame as a property and added a couple of keyframes:
Now back to our graph editor, and you will see a line like this:
For me it’s two lines because I animated two channels, X & RY.
Now you can click the handles and move the keyframes as much as you want.
Remember: Time is horizontal and Value is vertical. Meaning if you move the handles right or left, means you are increasing or decreasing the time, but on the other hand if you move the keyframe higher or lower, means you are increasing or decreasing the value of that channel
Now we can pick custom interpolation via Context menu by group selecting all keyframes and right clicking them
I choose Bezier curve interpolation, as linear is basically the lines we’ve just seen.
Once you pick Bezier interpolation, you can control the channel’s curve by the handles when selecting a keyframe
after editing:
Frequently Asked Questions (FAQ)
Q: Is Motion free?
Yes! Motion is completely free to use at this stage.
Q: Can I animate custom properties or only parts and rigs?
Motion can animate nearly any numeric property on any Roblox instance, including parts, cameras, rigs, colors, transparency, and more. Some string properties like .Text are still in progress.
Q: What interpolation methods does Motion support?
All Roblox’s native interpolations and custom ones like Bezier are supported.
Q: Is there a way to trigger events during animations?
Yes, you can add markers to your timeline and link callbacks using LinkMarkerAction.
Q: Can I import existing Roblox KeyframeSequences into Motion?
Importing is planned for an upcoming release, but not supported yet.










