```
local Amount = 5 -- amount of satellites to generate
local Speed = 1000 -- rotation speed
local TweenTime = 1 -- base tween time. might be modified later depending on speed
local TweenService = game:GetService('TweenService')
local Theta = math.pi * 2 / Amount
-- part generation
local Model = Instance.new('Model', workspace)
local Base = Instance.new('Part')
Base.Shape = Enum.PartType.Cylinder
Base.Size = Vector3.new(10, 10, 10)
Base.Color = Color3.fromRGB(0, 255, 0)
Base.BottomSurface = Enum.SurfaceType.Smooth
Base.TopSurface = Enum.SurfaceType.Smooth
Base.CanCollide = false
Base.Anchored = true
Base.CFrame = CFrame.new(0, 20, -20) * CFrame.Angles(0, math.rad(90), 0)
Base.RotVelocity = Vector3.new(0, 0, 50)
Model.PrimaryPart = Base
local Satellite = Instance.new('Part')
Satellite.Shape = Enum.PartType.Block
Satellite.Size = Vector3.new(10, 5, 5)
Satellite.BottomSurface = Enum.SurfaceType.Smooth
Satellite.TopSurface = Enum.SurfaceType.Smooth
Satellite.CanCollide = false
-- generate satellites around the base, pointing at the center
for i = 1, Amount do
local Angle = Theta * i
local Size = Base.Size.X
local X = Size * math.cos(Angle)
local Y = Size * math.sin(Angle)
local Z = Base.Position.Z
local newSatellite = Satellite:Clone()
newSatellite.Color = Color3.fromRGB(math.random(0, 255), 0, math.random(0, 255))
newSatellite.Parent = Model
newSatellite.CFrame = CFrame.new(Vector3.new(X + Base.Position.X, Y + Base.Position.Y, Z), Base.Position) * CFrame.Angles(math.rad(45),0, 0)
local newWeld = Instance.new('WeldConstraint',Base)
newWeld.Part0 = Base
newWeld.Part1 = newSatellite
end
Base.Parent = Model
-- clamp speed. if speed is too high, adjust tween time
Speed = math.clamp(Speed, 100, 10000)
if Speed > 1999 then
TweenTime = TweenTime / (((Speed - 1999) / 1999) + 1)
Speed = 1999
end
-- generate tween info and a dummy cframe value to be used for tweens
local Tween_Info = TweenInfo.new(TweenTime, Enum.EasingStyle.Linear, Enum.EasingDirection.InOut, 0, false, 0)
local DummyCFrame = Instance.new('CFrameValue')
DummyCFrame.Value = Model:GetPrimaryPartCFrame()
DummyCFrame:GetPropertyChangedSignal('Value'):Connect(function()
Model:SetPrimaryPartCFrame(DummyCFrame.Value)
end)
-- do the actual tween on a loop, adjusting the tween for its current position
while true do
local TweenCrusher = TweenService:Create(DummyCFrame, Tween_Info, {Value = DummyCFrame.Value * CFrame.Angles(math.pi / (1000 / (Speed / 2)), 0, 0)})
TweenCrusher:Play()
TweenCrusher.Completed:Wait()
end
```