Hard Light Productions Forums
Modding, Mission Design, and Coding => The Scripting Workshop => Topic started by: Black Wolf on October 17, 2010, 03:14:40 am
-
Is it possible to script in some sort of system where by debris is affected by gravity? ATM if you put a mission in an atmospheric skybox, the debris flies off ala zero G, which kind of kills the immersion a little bit. It'd be nice to have it fall down instead.
Possible?
[EDIT]I have tried to look into this myself, for the record, but scripting and programming is something I've had zero experience with. I got as far as isHull, and then realized I had no idea how to apply it :\.
-
For bigger debris bits it is possible to do. For the small debris shards i'm not sure
-
It actually very easy to implement :P
See this:
#Conditional Hooks
$Application: FS2_Open
$On Frame:
[
globalG = 9.81
for i=1,#mn.Debris do
local vec = ba.createVector(0, -1, 0)
vec = vec * globalG / 50
mn.Debris[i].Physics.Velocity = mn.Debris[i].Physics.Velocity + vec
end
]
#End
Gives cool results with the new mediavp effects ;7
-
I imagine it's easier to do with debris than with ships, since with debris, you don't have to worry about damping messing up your gravity math. :)
You may want to consider including some sort of "drag" factor as well, so the debris reaches terminal velocity instead of accelerating forever...
-
What about landscape? Once debris hit landscape, it will contnue to ram it. It is unevitable, I guess?
-
Debris tends to blow up when it collides with anything.
Cheers m!m, I'll try this out tonight :)
-
globalG = 9.81
Well it works for Earth at sea level. :p
-
Hmmm... Perhaps we could have variable geometry or a sexp which could set the value to be used by the script?
-
Hmmm... Perhaps we could have variable geometry or a sexp which could set the value to be used by the script?
May be possible for the script to simply read a SEXP variable.
-
Possible to make a script that makes a fighter/bomber start falling down if the speed is too low? I currently do it via events in FRED, but would be much better if it was in a script form and worked gradually.
-
Possible to make a script that makes a fighter/bomber start falling down if the speed is too low? I currently do it via events in FRED, but would be much better if it was in a script form and worked gradually.
This is possible and Nuke already showed it (check out his SVN (http://nukedspace.fsmods.net/svn/trunk/atmospheric_flight_model/)) but the AI can't handle it as tries to use the normal FS-physics.
Hmmm... Perhaps we could have variable geometry or a sexp which could set the value to be used by the script?
Could be done like General Battuta says or via the script-eval SEXP.
-
Oh! Dude! :D
Once I fiured out how to apply this only to individual missions, man - so cool :) **** looks awesome blowing up now :D
The only issues I have are that it doesn't always quite work right - very occasionally ou still have bits of debris that'll float away - I think this occurs when they bounce of the ground - but I can so deal with that - it's too awesome not to.
Thanks muchly :D
-
The only issues I have are that it doesn't always quite work right - very occasionally ou still have bits of debris that'll float away - I think this occurs when they bounce of the ground - but I can so deal with that - it's too awesome not to.
I have no idea what causes this as the script doesn't make a difference between debris.
EDIT: I think I found what was wrong. The script left out the first debris so the gravity wasn't applied.
And I added a few things that make it possible to control the gravity constant and also it's possible to simply disable the script from FRED and I also tried to include some kind of landscape mechanism, see below:
#Conditional Hooks
$Application: FS2_Open
$On Game Init:
[
function indexOf(t,val)
for k,v in ipairs(t) do
if v == val then
return k
end
end
end
function g_setG(value)
if type(value) ~= "number" then
ba.warning("Invalid type given to g_setG!")
return
end
globalG = value
end
function g_enable()
enabled = true
end
function g_disable()
enabled = false
end
function g_sGr(value)
local ship = mn.Ships[value]
if ship == nil or not ship:isValid() then
ba.warning("Invalid value given to g_sGr")
return
end
groundShip = ship
end
ignoreDebris = {}
globalG = 10
enabled = true
groundShip = nil
]
$On Debris Collision:
[
if hv.Self:getBreedName():lower() == "ship" and hv.Self == groundShip then
hv.Debris.Physics.Velocity = ba.createVector(0,0,0)
table.insert(ignoreDebris, hv.Debris)
end
]
$State: GS_STATE_GAME_PLAY
$On Frame:
[
if globalG and globalG <= 0 or not enabled then
return
end
for i=0,#mn.Debris do
if indexOf(ignoreDebris, mn.Debris[i]) then
return -- Don't apply gravity on things we ignore
end
local vec = ba.createVector(0, -1, 0)
vec = vec * globalG / 50
local newVec = mn.Debris[i].Physics.Velocity + vec
mn.Debris[i].Physics.Velocity = newVec
end
]
#End
Interaction is possible via the script-eval SEXP:
use script-eval with g_setG(<some numeric value> as first Argument to set the gravity constant,
use it with g_enable() or g_disable() to enable/disable the script
and use g_sGr(<some ship name>) to activate the landscape mode for that ship though I'm not sure if it will work :nervous:
-
What happens if you use this to apply gravity to ships?
-
Basically it would work but it will result in funny effect when the AI tries to get to a ship or a waypoint :D
-
Basically it would work but it will result in funny effect when the AI tries to get to a ship or a waypoint :D
I don't suppose I can talk you into modifying the script so that it affects any ship with the "affected by gravity" flag set? :)
-
I don't suppose I can talk you into modifying the script so that it affects any ship with the "affected by gravity" flag set? :)
Well, AFAIK there's no possibility to access the flags from scripting but there's that neat SCP-badge right under your name so could you maybe make it available or help me find where I can find the flags in the code so I can do it on my own? :)
-
Say...
Fringespace has a need for "gravitized" objects... would it be possible to develop this into "point gravity" within a specified object, and then use a scrpit, whether it's based on Newton's Law of Gravitation or something else (a variable gravity system dependant on range) , to ramp up the intensity of gravity upon a given target, whether it's the player ship or his wreckage?
-
I don't suppose I can talk you into modifying the script so that it affects any ship with the "affected by gravity" flag set? :)
Well, AFAIK there's no possibility to access the flags from scripting but there's that neat SCP-badge right under your name so could you maybe make it available or help me find where I can find the flags in the code so I can do it on my own? :)
The flag you want is SF2_AFFECTED_BY_GRAVITY. If you can't access it from scripting, though, that's a problem. Since I know practically nothing about the scripting code, I have no idea how to fix it, but hopefully that can be rectified (or someone else can do it :p).
-
Ok, got a function up that works (patch is attached).
Using this the script can apply the gravity on every ship that has this flag.
[attachment deleted by admin]
-
Fantastic! So AI will of course still freak out and fail, but at least it's progress.
-
Wow, get lift and stalling working and you'll be on your way to an arcade-style atmospheric flight model :yes:
-
It's already working (http://nukedspace.fsmods.net/svn/trunk/atmospheric_flight_model/) :p
-
Awesome! I'll take this for a spin when I get home. :)
Don't we need an updated version of the script that looks for ships with the flag and applies gravity to them?
Also, atmospheric flight is only part of the coolness this allows. I think that if we combine gravity with the landing code, we'll be able to get working land vehicles, such as tanks and pod racers. :D
-
You're right! :nod:
#Conditional Hooks
$Application: FS2_Open
$On Game Init:
[
function indexOf(t,val)
for k,v in ipairs(t) do
if v == val then
return k
end
end
end
function g_setG(value)
if type(value) ~= "number" then
ba.warning("Invalid type given to g_setG!")
return
end
globalG = value
end
function g_enable()
enabled = true
end
function g_disable()
enabled = false
end
function g_sGr(value)
local ship = mn.Ships[value]
if ship == nil or not ship:isValid() then
ba.warning("Invalid value given to g_sGr")
return
end
groundShip = ship
end
function doGravity(object)
local vec = ba.createVector(0, -1, 0)
vec = vec * globalG
local newVec = object.Physics.Velocity + vec
object.Physics.Velocity = newVec
end
ignoreDebris = {}
globalG = 10
enabled = true
groundShip = nil
]
$On Debris Collision:
[
if hv.Self:getBreedName():lower() == "ship" and hv.Self == groundShip then
hv.Debris.Physics.Velocity = ba.createVector(0,0,0)
table.insert(ignoreDebris, hv.Debris)
end
]
$State: GS_STATE_GAME_PLAY
$On Frame:
[
if globalG and globalG <= 0 or not enabled then
return
end
for i=0,#mn.Debris do
if indexOf(ignoreDebris, mn.Debris[i]) then
return -- Don't apply gravity on things we ignore
end
doGravity(mn.Debris[i])
end
for i=0, #mn.Ships do
if mn.Ships[i].FlagAffectedByGravity then
doGravity(mn.Ships[i])
end
end
]
#End
Warning: This script will only work with a build that includes the posted patch!
EDIT: Fixed bugs...
-
Function added to trunk in revision 6669
-
With an atmospheric skybox, this would be a nice touch with models like this (http://www.hard-light.net/forums/index.php?topic=72107.0) blowing up everywhere.
-
ZOMG@everythinginthisthread!
-
So, question, will this now mean than only ships with "Affected by Gravity" will have their debris fall down? Because for my purposes, I'd much rather have it set up the way it was, i.e. every ship's debris falls down, but only selected ships (until AI gets smarter, just the player) have to eal with gravity while flying.
I'd test it and ee, but I'm not sure whgat to do with that .patch file :nervous:
-
So, question, will this now mean than only ships with "Affected by Gravity" will have their debris fall down? Because for my purposes, I'd much rather have it set up the way it was, i.e. every ship's debris falls down, but only selected ships (until AI gets smarter, just the player) have to eal with gravity while flying.
I'd test it and ee, but I'm not sure whgat to do with that .patch file :nervous:
the patch is for coders
-
A couple of things I've noticed about the script:
1. Last doGravity call should be on mn.Ships, not mn.Debris
2. No adjustment for framerate... I added this by replacing "globalG / 50" in doGravity with "globalG * ba.getFrametime()"
3. Unfortunately, it doesn't work very well on ships unless they have high damp, and then the ship gets unflyable. Even then, terminal velocity is pretty low overall. We're going to have to get creative with how gravity is applied to ships so that we get something reasonable for ships of all damping levels... not sure what.
The debris part works great, though.
EDIT: Where did those italics come from?
-
I think implementing terminal velocity would be beneficial to this system.
Not only is it mathematically reasonably simple, but it's also going to work as a rudimentary atmospheric friction model.
The maths of it goes like this:
F = -G - kv^n
where
F is the resultant force vector
G is gravitational force (weight) (G=-mg)
k is friction coefficient (determined from values such as shape coefficient and air density)
v is velocity
n is the exponent for velocity, which varies depending on the speed itself, but for a rudimentary system it's more or less safe to approximate that n = 2. Basically this number increases as velocity increases, but that makes the equation needlessly complicated. Usually the friction coefficient is experimentally defined and ranges from zero to 1; for most FS2 ships I suppose it would range between 0.5 and 1.
As for solving the equation, using n = 2:
F = dp/dt = m dv/dt
m dv/dt = -mg - kv^2
dv/dt = -g - (k/m) v^2
1 / (-g - (k/m)v^2) dv = dt || Int(..)
v t
∫ 1 / (-g - (k/m)v^2) dv = ∫ dt
v0 t0
...
v(t) = - (√g√m / √k) * tan ( [√g√k) / √m] t - arctan [(√k / √g√m) v0] )
And there you go; of course, this is a simplified equation where movement is limited to one axis. If you allow movement in all three dimensions, then you have to formulate the air friction so that it's always vectorized against the velocity vector, while gravitational force always pulls "down" (in homogenous gravity field approximation, that's the same direction everywhere in the game world).
If you can hook accelerations into the engine directly instead of velocities, that would make things easier still, since solving the diff eq wouldn't be even necessary, you could just plug the forces divided by mass into the engine and it would apply the accelerations to objects.
-
I read 'terminal velocity' and thought of this:
(http://www.3drealms.com/images/books/tvbook.gif)
-
Well, yes, a lot of problems would be solved if Freespace used a clear-cut "sum the forces on the body" model like you learn in any first-year physics class. Basic kinematics. For better or for worse, they did something more complicated with damping and ramped desired velocities that makes it a lot harder to just add arbitrary forces to the model. That's what makes this such an annoying problem. :) If they'd done it the simple way Herra just described, adding gravity would be trivial. Unfortunately, they didn't, so it's not. :(
-
Well, yes, a lot of problems would be solved if Freespace used a clear-cut "sum the forces on the body" model like you learn in any first-year physics class. Basic kinematics. For better or for worse, they did something more complicated with damping and ramped desired velocities that makes it a lot harder to just add arbitrary forces to the model. That's what makes this such an annoying problem. :) If they'd done it the simple way Herra just described, adding gravity would be trivial. Unfortunately, they didn't, so it's not. :(
Blast and damnation. Good to know, then...
-
For relatively high damping values ($Damp > 2.0 or so) this script actually works pretty well.
I think if we can come up with the right equation, we can adjust the force based on the ship's damping value and have a fairly reasonable approximation that gives about the same effective amount of gravity for different values of damp.
By the way, gravity + landings code didn't lead to land vehicle awesomeness as easily as I had hoped. :( Oh well, back to the drawing board!
-
For relatively high damping values ($Damp > 2.0 or so) this script actually works pretty well.
I think if we can come up with the right equation, we can adjust the force based on the ship's damping value and have a fairly reasonable approximation that gives about the same effective amount of gravity for different values of damp.
This might work very well.
By the way, gravity + landings code didn't lead to land vehicle awesomeness as easily as I had hoped. :( Oh well, back to the drawing board!
That's sad :(
So, question, will this now mean than only ships with "Affected by Gravity" will have their debris fall down? Because for my purposes, I'd much rather have it set up the way it was, i.e. every ship's debris falls down, but only selected ships (until AI gets smarter, just the player) have to eal with gravity while flying.
Gravity is applied to all debris in the mission and to the ships that carry the "affected-by-gravity" flag.
Well, yes, a lot of problems would be solved if Freespace used a clear-cut "sum the forces on the body" model like you learn in any first-year physics class. Basic kinematics. For better or for worse, they did something more complicated with damping and ramped desired velocities that makes it a lot harder to just add arbitrary forces to the model. That's what makes this such an annoying problem. :) If they'd done it the simple way Herra just described, adding gravity would be trivial. Unfortunately, they didn't, so it's not. :(
And it's very difficult to implement I suppose? :(
There are too much sad smilies in this post...
-
Hmm... There should be functions/tools in fs open lua for checking bits inside flags but i suppose a direct function is ok as well.
As for how to deal with ground... Setting all terrain pieces (& buildings, scenery etc stuff) into same collision group (see scripting html) to drastically reduce the number of collision checks needed would be advisable. Also using directed ray collision with the terrain pieces allows you to create a crude 'radar altimeter'. Same idea could work with vehicles.
-
May that script affect disabled ships/object as well?
I thought about a sort of flying city where when you destroy the underneath engine that maintain it to the sky... after destroying those you'll have this object falling to the "ground"
-
This could be done by setting the "affected-by-gravity" flag when the engine is destroyed. I don't know if there is a SEXP capable of doing this but it can be done without changes to the script. :nod:
-
*Mega bump*
I don't know how to use scripts or implement this. Can someone please explain? Thank you.
-
Copy the code in this thread into a table called for example gravity-sct.tbm and place it into your data/tables directory.
There you go! :)
-
Thank you! :)