|
| 13 Apr 2013 06:28 PM |
How would I do a "physics" explosion?
I mean, basically an explosion without the effect. I was thinking if I should insert bodyforces to near parts and make them fly away. I don't know how to direct the bodyforces away from the point of explosions though. |
|
|
| Report Abuse |
|
|
iStone4S
|
  |
| Joined: 07 May 2012 |
| Total Posts: 416 |
|
|
| 13 Apr 2013 06:32 PM |
| The vector3 would be (hit.Position - explosion.Position).unit*number |
|
|
| Report Abuse |
|
|
harryx
|
  |
| Joined: 25 Oct 2008 |
| Total Posts: 3209 |
|
|
| 13 Apr 2013 06:32 PM |
p.Velocity = (p.Position-exp.Position).unit*300
Try that, p being the part being hit and exp being a part on the source of the explosion. |
|
|
| Report Abuse |
|
|
iStone4S
|
  |
| Joined: 07 May 2012 |
| Total Posts: 416 |
|
|
| 13 Apr 2013 06:33 PM |
| One does not simply have the same idea as me. |
|
|
| Report Abuse |
|
|
harryx
|
  |
| Joined: 25 Oct 2008 |
| Total Posts: 3209 |
|
| |
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 13 Apr 2013 06:36 PM |
But that would affect everything the same, but what should happen is that the further it is, the less it gets affected.
local explosionPosition = Vector3.new(0, 0, 0); local explosionRadius = 20; local explosionPressure = 300; foreach (part in radius) -- Code this bit yourself local vecToCenter = part.Position - explosionPosition; local dist = vecToCenter.magnitude; part.Velocity = (vecToCenter.unit * explosionPressure) * (explosionRadius - dist); end
I think? |
|
|
| Report Abuse |
|
|
|
| 13 Apr 2013 06:40 PM |
p.Velocity = (p.Position - e.Position).unit * math.max(0, e.BlastRadius - (p.Position - e.Position).magnitude * (0.25 * e.BlastPressure)
Might work, might not. Meh. |
|
|
| Report Abuse |
|
|
|
| 13 Apr 2013 06:44 PM |
| droideka, ill test with that in a bit |
|
|
| Report Abuse |
|
|
iStone4S
|
  |
| Joined: 07 May 2012 |
| Total Posts: 416 |
|
| |
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 13 Apr 2013 06:59 PM |
@iStone: ty
@Arceus: Ah yes, I should have added math.max(0, explosionRadius - dist) to mine. Lol far away objects would go in the oppsite direction... |
|
|
| Report Abuse |
|
|
woot3
|
  |
| Joined: 10 Nov 2008 |
| Total Posts: 3599 |
|
|
| 13 Apr 2013 07:05 PM |
| I don't know why, but I am always in the habit of doing CFrame.new(A,B).lookVector instead of (A-B).unit I have a feeling Oysi posted something ages ago, or sdfgw did and it just left me typing the first method all the time. |
|
|
| Report Abuse |
|
|
|
| 13 Apr 2013 07:23 PM |
@woot
I did that up until a week ago, when I finally figured out what a unit vector is. |
|
|
| Report Abuse |
|
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 13 Apr 2013 07:24 PM |
@2 above comments lol
vectors <3 though I'm still a bit ehh on dot and cross products |
|
|
| Report Abuse |
|
|
|
| 13 Apr 2013 11:12 PM |
I have this made from droideka's. The parts in the radius only nudge a little bit, and when function is ran for the 3rd-5 th. time, the parts dissapear.
function physics_explosion(pos,rad,pres,phys_ents) local explosionPosition = pos local explosionRadius = rad local explosionPressure = pres * 10 for i = 1, #phys_ents do if phys_ents[i].ClassName == "Part" then if phys_ents[i].Anchored == false then if (phys_ents[i].Position - explosionPosition).magnitude <= explosionRadius then local vecToCenter = phys_ents[i].Position - explosionPosition local dist = vecToCenter.magnitude print("vel") phys_ents[i].Velocity = (vecToCenter.unit * explosionPressure) * (math.max(0, explosionRadius - dist)) end end end end end
physics_explosion(Vector3.new(0, 0, 0),30,1000,workspace:children()) |
|
|
| Report Abuse |
|
|
woot3
|
  |
| Joined: 10 Nov 2008 |
| Total Posts: 3599 |
|
|
| 14 Apr 2013 03:31 AM |
I haven't really looked at yours as obviously it's working. But personally I would do...
function Explode(Pos,Rad,Pres,Par) local Pres = Pres*100 for i,v in pairs(Par:GetChildren()) do if (v:IsA'Part' or v:IsA'WedgePart' or v:IsA'Seat' or v:IsA'VehicleSeat' or v:IsA'CornerWedgePart') and (not v.Anchored) and (v.Position-Pos).magnitude < Rad then --v:BreakJoints() You may want to add this. v.Velocity = (v.Position-Pos).unit*(Pres/(v.Position-Pos.magnitude)) end end end
Explode(Vector3.new(0,0,0),30,1000,workspace)
It's basically the same as yours, but the velocity calculation is different. It may not be the best, or rather far from it. But you'll get a different reaction. Just tinker with it :P
Also, you may want to add :BreakJoints() |
|
|
| Report Abuse |
|
|
|
| 14 Apr 2013 05:20 AM |
| I would just breakjoints the part and change its velocity (by an amount that corresponds with the force you wanted) because bodyforces might not work properly (youd want them to be there for a single frame...) |
|
|
| Report Abuse |
|
|
|
| 14 Apr 2013 07:54 AM |
@woot3
LOL, Vector3 expected, got number, on line: v.Velocity = (v.Position-Pos).unit*(Pres/(v.Position-Pos.magnitude)) |
|
|
| Report Abuse |
|
|
|
| 14 Apr 2013 07:55 AM |
| I think its the pressure on that line that fails, since its a number. |
|
|
| Report Abuse |
|
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 14 Apr 2013 07:56 AM |
v.Velocity = (v.Position-Pos).unit*(Pres/(v.Position-Pos.magnitude)) A ) is in the wrong place, should be: v.Velocity = (v.Position - Pos).unit * (Pres / (v.Position - Pos).magnitude) |
|
|
| Report Abuse |
|
|
|
| 14 Apr 2013 08:02 AM |
The same thing happens with that code.
No matter how large the pressure is, the parts just shake very little, and stop. It prints "0,0,0" on every explosion, but after like, 10 explosions, then the parts dissapear(fly very fast), and it prints velocities over 200k.
function phys_explosion(Pos,Rad,Pres,Par) local Pres = Pres*100 for i,v in pairs(Par:GetChildren()) do if (v:IsA'Part' or v:IsA'WedgePart' or v:IsA'Seat' or v:IsA'VehicleSeat' or v:IsA'CornerWedgePart') and (not v.Anchored) and (v.Position-Pos).magnitude < Rad then v:BreakJoints() v.Velocity = (v.Position - Pos).unit * (Pres / (v.Position - Pos).magnitude) print(v.Velocity) end end end
phys_explosion(Vector3.new(0,0,0),30,100000,workspace) |
|
|
| Report Abuse |
|
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 14 Apr 2013 08:19 AM |
Aha, I believe I've worked it out! You need to anchor the part, then set velocity, then unanchor it. Here's my code:
local Explosion = { }; Explosion.new = function (center, radius, pressure) print("Exploding"); local b = Instance.new("Part"); b.FormFactor = "Symmetric"; b.Shape = "Ball"; b.Size = Vector3.new(radius * 2, radius * 2, radius * 2); b.Transparency = 0.5; b.BrickColor = BrickColor.new("Bright red"); b.CanCollide = false; b.Anchored = true; b.CFrame = CFrame.new(center); b.TopSurface = "Smooth"; b.BottomSurface = "Smooth"; b.Parent = workspace; delay(1, function () b:Destroy(); end); for _, p in pairs(workspace:GetChildren()) do repeat if ((not p:IsA("BasePart")) or (p:IsA("Terrain"))) then break; end if (p.Anchored) then break; end local vecToCenter = p.Position - center; local distFromCenter = vecToCenter.magnitude; if (distFromCenter > radius) then break; end print("Object "..p.Name.." going boom"); p:BreakJoints(); p.BrickColor = BrickColor.new("Bright black"); local vec = vecToCenter.unit * pressure; local scalar = radius - distFromCenter; local vel = vec * scalar; print("Vec to set to: "..tostring(vel)); p.Anchored = true; p.Velocity = vel; print("Actual vel: "..tostring(p.Velocity)); p.Anchored = false; print(); until (true); end end;
wait(2); Explosion.new(Vector3.new(0, 0, 0), 20, 10); |
|
|
| Report Abuse |
|
|
|
| 14 Apr 2013 08:22 AM |
Oh, well that anchoring worked, wow.
Thanks! :D |
|
|
| Report Abuse |
|
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 14 Apr 2013 08:24 AM |
Lol mine definitely worked... imgur /peAhZSV.png
Yw :3 |
|
|
| Report Abuse |
|
|
Dr01d3k4
|
  |
| Joined: 11 Oct 2007 |
| Total Posts: 17916 |
|
|
| 14 Apr 2013 08:43 AM |
I've improved mine so that it will either use a recursive approach to get every part, or region3 cause it's quicker:
local Explosion = { };
local function blowUpPart(p, center, radius, pressure) if ((p:IsA("BasePart")) and (not p:IsA("Terrain"))) then if (not p.Anchored) then local vecToCenter = p.Position - center; local distFromCenter = vecToCenter.magnitude; if (distFromCenter <= radius) then p:BreakJoints(); p.Anchored = true; p.Velocity = vecToCenter.unit * (pressure * (radius - distFromCenter)); p.Anchored = false; end end end end
Explosion.new = function (center, radius, pressure, all) local b = Instance.new("Part"); b.FormFactor = "Symmetric"; b.Shape = "Ball"; b.Size = Vector3.new(radius * 2, radius * 2, radius * 2); b.Transparency = 0.5; b.BrickColor = BrickColor.new("Bright red"); b.CanCollide = false; b.Anchored = true; b.CFrame = CFrame.new(center); b.TopSurface = "Smooth"; b.BottomSurface = "Smooth"; b.Parent = workspace; delay(1, function () b:Destroy(); end); if (all) then local function explode(m) for _, p in pairs(m:GetChildren()) do if ((p:IsA("BasePart")) and (not p:IsA("Terrain"))) then blowUpPart(p, center, radius, pressure); elseif (p:IsA("Model")) then explode(p); end end end explode(workspace); else print("Easy way"); local radVec = Vector3.new(radius, radius, radius); local parts = workspace:FindPartsInRegion3(Region3.new(center - radVec, center + radVec), nil, 100); for _, p in pairs(parts) do blowUpPart(p, center, radius, pressure); end end end;
wait(0.5); Explosion.new(Vector3.new(0, 0, 0), 40, 5); |
|
|
| Report Abuse |
|
|
woot3
|
  |
| Joined: 10 Nov 2008 |
| Total Posts: 3599 |
|
|
| 14 Apr 2013 09:22 AM |
| Sorry, I was just throwing something out there, more to have a look at than anything more. |
|
|
| Report Abuse |
|
|