Advertisement
isaiah_yt110

qPerfectionWeld (script)

Apr 16th, 2021
922
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 7.12 KB | None | 0 0
  1. -- Created by Quenty (@Quenty, follow me on twitter).
  2. -- Should work with only ONE copy, seamlessly with weapons, trains, et cetera.
  3. -- Parts should be ANCHORED before use. It will, however, store relatives values and so when tools are reparented, it'll fix them.
  4.  
  5. --[[ INSTRUCTIONS
  6. - Place in the model
  7. - Make sure model is anchored
  8. - That's it. It will weld the model and all children.
  9.  
  10. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  11. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  12. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  13. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  14. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  15. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  16. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  17. THIS SCRIPT SHOULD BE USED ONLY BY ITSELF. THE MODEL SHOULD BE ANCHORED.
  18.  
  19. This script is designed to be used is a regular script. In a local script it will weld, but it will not attempt to handle ancestory changes.
  20. ]]
  21.  
  22. --[[ DOCUMENTATION
  23. - Will work in tools. If ran more than once it will not create more than one weld. This is especially useful for tools that are dropped and then picked up again.
  24. - Will work in PBS servers
  25. - Will work as long as it starts out with the part anchored
  26. - Stores the relative CFrame as a CFrame value
  27. - Takes careful measure to reduce lag by not having a joint set off or affected by the parts offset from origin
  28. - Utilizes a recursive algorith to find all parts in the model
  29. - Will reweld on script reparent if the script is initially parented to a tool.
  30. - Welds as fast as possible
  31. ]]
  32.  
  33. -- qPerfectionWeld.lua
  34. -- Created 10/6/2014
  35. -- Author: Quenty
  36. -- Version 1.0.3
  37.  
  38. -- Updated 10/14/2014 - Updated to 1.0.1
  39. --- Bug fix with existing ROBLOX welds ? Repro by asimo3089
  40.  
  41. -- Updated 10/14/2014 - Updated to 1.0.2
  42. --- Fixed bug fix.
  43.  
  44. -- Updated 10/14/2014 - Updated to 1.0.3
  45. --- Now handles joints semi-acceptably. May be rather hacky with some joints. :/
  46.  
  47. local NEVER_BREAK_JOINTS = false -- If you set this to true it will never break joints (this can create some welding issues, but can save stuff like hinges).
  48.  
  49.  
  50. local function CallOnChildren(Instance, FunctionToCall)
  51. -- Calls a function on each of the children of a certain object, using recursion.
  52.  
  53. FunctionToCall(Instance)
  54.  
  55. for _, Child in next, Instance:GetChildren() do
  56. CallOnChildren(Child, FunctionToCall)
  57. end
  58. end
  59.  
  60. local function GetNearestParent(Instance, ClassName)
  61. -- Returns the nearest parent of a certain class, or returns nil
  62.  
  63. local Ancestor = Instance
  64. repeat
  65. Ancestor = Ancestor.Parent
  66. if Ancestor == nil then
  67. return nil
  68. end
  69. until Ancestor:IsA(ClassName)
  70.  
  71. return Ancestor
  72. end
  73.  
  74. local function GetBricks(StartInstance)
  75. local List = {}
  76.  
  77. -- if StartInstance:IsA("BasePart") then
  78. -- List[#List+1] = StartInstance
  79. -- end
  80.  
  81. CallOnChildren(StartInstance, function(Item)
  82. if Item:IsA("BasePart") then
  83. List[#List+1] = Item;
  84. end
  85. end)
  86.  
  87. return List
  88. end
  89.  
  90. local function Modify(Instance, Values)
  91. -- Modifies an Instance by using a table.
  92.  
  93. assert(type(Values) == "table", "Values is not a table");
  94.  
  95. for Index, Value in next, Values do
  96. if type(Index) == "number" then
  97. Value.Parent = Instance
  98. else
  99. Instance[Index] = Value
  100. end
  101. end
  102. return Instance
  103. end
  104.  
  105. local function Make(ClassType, Properties)
  106. -- Using a syntax hack to create a nice way to Make new items.
  107.  
  108. return Modify(Instance.new(ClassType), Properties)
  109. end
  110.  
  111. local Surfaces = {"TopSurface", "BottomSurface", "LeftSurface", "RightSurface", "FrontSurface", "BackSurface"}
  112. local HingSurfaces = {"Hinge", "Motor", "SteppingMotor"}
  113.  
  114. local function HasWheelJoint(Part)
  115. for _, SurfaceName in pairs(Surfaces) do
  116. for _, HingSurfaceName in pairs(HingSurfaces) do
  117. if Part[SurfaceName].Name == HingSurfaceName then
  118. return true
  119. end
  120. end
  121. end
  122.  
  123. return false
  124. end
  125.  
  126. local function ShouldBreakJoints(Part)
  127. --- We do not want to break joints of wheels/hinges. This takes the utmost care to not do this. There are
  128. -- definitely some edge cases.
  129.  
  130. if NEVER_BREAK_JOINTS then
  131. return false
  132. end
  133.  
  134. if HasWheelJoint(Part) then
  135. return false
  136. end
  137.  
  138. local Connected = Part:GetConnectedParts()
  139.  
  140. if #Connected == 1 then
  141. return false
  142. end
  143.  
  144. for _, Item in pairs(Connected) do
  145. if HasWheelJoint(Item) then
  146. return false
  147. elseif not Item:IsDescendantOf(script.Parent) then
  148. return false
  149. end
  150. end
  151.  
  152. return true
  153. end
  154.  
  155. local function WeldTogether(Part0, Part1, JointType, WeldParent)
  156. --- Weld's 2 parts together
  157. -- @param Part0 The first part
  158. -- @param Part1 The second part (Dependent part most of the time).
  159. -- @param [JointType] The type of joint. Defaults to weld.
  160. -- @param [WeldParent] Parent of the weld, Defaults to Part0 (so GC is better).
  161. -- @return The weld created.
  162.  
  163. JointType = JointType or "Weld"
  164. local RelativeValue = Part1:FindFirstChild("qRelativeCFrameWeldValue")
  165.  
  166. local NewWeld = Part1:FindFirstChild("qCFrameWeldThingy") or Instance.new(JointType)
  167. Modify(NewWeld, {
  168. Name = "qCFrameWeldThingy";
  169. Part0 = Part0;
  170. Part1 = Part1;
  171. C0 = CFrame.new();--Part0.CFrame:inverse();
  172. C1 = RelativeValue and RelativeValue.Value or Part1.CFrame:toObjectSpace(Part0.CFrame); --Part1.CFrame:inverse() * Part0.CFrame;-- Part1.CFrame:inverse();
  173. Parent = Part1;
  174. })
  175.  
  176. if not RelativeValue then
  177. RelativeValue = Make("CFrameValue", {
  178. Parent = Part1;
  179. Name = "qRelativeCFrameWeldValue";
  180. Archivable = true;
  181. Value = NewWeld.C1;
  182. })
  183. end
  184.  
  185. return NewWeld
  186. end
  187.  
  188. local function WeldParts(Parts, MainPart, JointType, DoNotUnanchor)
  189. -- @param Parts The Parts to weld. Should be anchored to prevent really horrible results.
  190. -- @param MainPart The part to weld the model to (can be in the model).
  191. -- @param [JointType] The type of joint. Defaults to weld.
  192. -- @parm DoNotUnanchor Boolean, if true, will not unachor the model after cmopletion.
  193.  
  194. for _, Part in pairs(Parts) do
  195. if ShouldBreakJoints(Part) then
  196. Part:BreakJoints()
  197. end
  198. end
  199.  
  200. for _, Part in pairs(Parts) do
  201. if Part ~= MainPart then
  202. WeldTogether(MainPart, Part, JointType, MainPart)
  203. end
  204. end
  205.  
  206. if not DoNotUnanchor then
  207. for _, Part in pairs(Parts) do
  208. Part.Anchored = false
  209. end
  210. MainPart.Anchored = false
  211. end
  212. end
  213.  
  214. local function PerfectionWeld()
  215. local Tool = GetNearestParent(script, "Tool")
  216.  
  217. local Parts = GetBricks(script.Parent)
  218. local PrimaryPart = Tool and Tool:FindFirstChild("Handle") and Tool.Handle:IsA("BasePart") and Tool.Handle or script.Parent:IsA("Model") and script.Parent.PrimaryPart or Parts[1]
  219.  
  220. if PrimaryPart then
  221. WeldParts(Parts, PrimaryPart, "Weld", false)
  222. else
  223. warn("qWeld - Unable to weld part")
  224. end
  225.  
  226. return Tool
  227. end
  228.  
  229. local Tool = PerfectionWeld()
  230.  
  231.  
  232. if Tool and script.ClassName == "Script" then
  233. --- Don't bother with local scripts
  234.  
  235. script.Parent.AncestryChanged:connect(function()
  236. PerfectionWeld()
  237. end)
  238. end
  239.  
  240. -- Created by Quenty (@Quenty, follow me on twitter).
  241.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement