Is this the best way to scale a model?

For some reason, OP’s code doesn’t work for a model I was trying to scale. If you get weird scaling behavior in the future when trying to use the code, this code works for me:

function scaleModel(model, scale)
	local origin = model.PrimaryPart.Position
	
	for _, part in ipairs(model:GetDescendants()) do
		if part:IsA("BasePart") then
			local pos = part.Position
			local rotCf = part.CFrame - pos
			local fromOriginDir = pos - origin
			part.Size *= Vector3.new(scale, scale, scale)
			part.CFrame = rotCf + origin + fromOriginDir*scale
		end
	end
end
25 Likes

I made @rbxts package for scale-model because this could be a little tricky. It needs to scale bunch of different kinds of sub-objects. For example, my package can scale Fire, Attachments, and even a NumberSequence inside of a ParticleEmitter.

You can install it to roblox-ts solution with npm i @rbxts/scale-model
Sourcecode in Typescript could be found on my Github

I made a roblox-ts Playground which will show the sourcecode compiled to Lua, however it’s not very human-friendly.

3 Likes

There is a scale model plugin that I use. Model Resize Plugin 2.1 [ DRAG TO RESIZE! ] - Roblox

Cool, yep, I knew about that, but I need to resize Models at runtime with script.

3 Likes

I’m using model:GetBoundingBox() as the primaryCf. I run the function the first time to scale it down, and then tween it back to its original size using the same function.

And for some reason the model always ends up rotated 180 degrees, is there a way to fix this? I’m not really experienced in Cframes so I would really appreciate it if someone could fix it…

How can I adjust this to work “down-up”?
Like if the scale would be adjusted with the scale tool in studio

Sorry for the bump, but I revised the functions mentioned here to also account for welded models. In this thread there are functions that delete the welds altogether, but that is not practical if those welds are needed. I simply adjust the offset of the joints’ C0 and C1 values based on the scale variable.

Thought this may be useful for others, so here it is:

function scaleModelWithJoints(model, scale)
	local origin = model.PrimaryPart.Position

	for _, obj in ipairs(model:GetDescendants()) do
		if obj:IsA("BasePart") then
			obj.Size = obj.Size*scale

			local distance = (obj.Position - model:GetPrimaryPartCFrame().p)
			local rotation = (obj.CFrame - obj.Position)
			obj.CFrame = (CFrame.new(model:GetPrimaryPartCFrame().p + distance*scale) * rotation)
		elseif obj:IsA("JointInstance") then
			local c0NewPos = obj.C0.p*scale
			local c0RotX, c0RotY, c0RotZ = obj.C0:ToEulerAnglesXYZ()
			
			local c1NewPos = obj.C1.p*scale
			local c1RotX, c1RotY, c1RotZ = obj.C1:ToEulerAnglesXYZ()

			obj.C0 = CFrame.new(c0NewPos)*CFrame.Angles(c0RotX, c0RotY, c0RotZ)
			obj.C1 = CFrame.new(c1NewPos)*CFrame.Angles(c1RotX, c1RotY, c1RotZ)
		end
	end
end

This function also allows the function to be scaled to a larger size which is what some of the functions listed in this thread were unable to do.

14 Likes

You could use multiple threads to speed it up

For some reason I used this code and I have an issue where a union welded onto a model would be in the wrong orientation when using this function

Do you have any plans to add ‘bones’ to the scaling? I am trying to scale a mesh with bones at runtime, and though it scales perfect, with the studio scaling tool, when I try to do it myself in code, I can’t get the bones to scale correctly.

As of March 2023, we now have the Model.Scale property, which can be set within Roblox Studio. We also have the Model:ScaleTo(scale) and Model:GetScale() methods, which can be used during runtime (and in Studio).

A lot of people reference this post, so I wanted to make one final post here about the official way to scale a model.

13 Likes

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.