GusPT Posted June 3, 2021 Share Posted June 3, 2021 Hi, I'm currently working on a A2A training mission, using lua and MIST, and would like to be able to spawn units in a position between 9 and 3' o clock in front of a given unit. I got the spawning and all that figured down, but I'm struggling with the math to determine the new unit position. Something like this: -- positionVec3: reference unit getPosition().p function cloneGroup(groupName, positionVec3) ... transform position to a place point between 9 and 3' o clock in front of the reference unit local teleportVars = { groupName = groupName, newGroupName = newGroupName, point = positionVec3, action = "clone", innerRadius = 4000, radius = 5000 } local _group = mist.teleportToPoint(teleportVars) local group = Group.getByName(_group.name) group:activate() return group end I'd truly appreciate if anyone could provide an example or point me in the right direction. Thanks! Link to comment Share on other sites More sharing options...
Hardcard Posted June 3, 2021 Share Posted June 3, 2021 (edited) I looked into offset points a couple of years ago, @funkyfranky was kind enough to assist and he ended up creating a MOOSE function that returns a vec3 point, offset from a chosen unit by a desired distance in all three axes. You basically introduce the desired offset in meters for each axis, the function will take care of the math. Most of it is standard Lua, you should have no trouble adapting it to MIST. Note that :GetOrientationX(), :GetOrientationY() and :GetOrientationZ() are the MOOSE way of accessing the DCS orientation tables returned by :getPosition() (x, y and z subtables only, not the p subtable). Here's the function. function POSITIONABLE:GetOffsetCoordinate(x,y,z) -- Default if nil. x=x or 0 y=y or 0 z=z or 0 -- Vectors making up the coordinate system. local X=self:GetOrientationX() local Y=self:GetOrientationY() local Z=self:GetOrientationZ() -- Offset vector: x meters ahead, z meters starboard, y meters above. local A={x=x, y=y, z=z} -- Scale components of orthonormal coordinate vectors. local x={x=X.x*A.x, y=X.y*A.x, z=X.z*A.x} local y={x=Y.x*A.y, y=Y.y*A.y, z=Y.z*A.y} local z={x=Z.x*A.z, y=Z.y*A.z, z=Z.z*A.z} -- Add up vectors in the unit coordinate system ==> this gives the offset vector relative the the origin of the map. local a={x=x.x+y.x+z.x, y=x.y+y.y+z.y, z=x.z+y.z+z.z} -- Vector from the origin of the map to the unit. local u=self:GetVec3() -- Translate offset vector from map origin to the unit: v=u+a. local v={x=a.x+u.x, y=a.y+u.y, z=a.z+u.z} local coord=COORDINATE:NewFromVec3(v) -- Return the offset coordinate. return coord end Here's a version of this script that I made for a test mission, using variables rather than tables, perhaps you'll find it easier to work with: function() local Cargo = UNIT:FindByName("Cargo") -- Vectors making up the coordinate system. local CargoXX = Cargo:GetOrientationX().x local CargoXY = Cargo:GetOrientationX().y local CargoXZ = Cargo:GetOrientationX().z local CargoYX = Cargo:GetOrientationY().x local CargoYY = Cargo:GetOrientationY().y local CargoYZ = Cargo:GetOrientationY().z local CargoZX = Cargo:GetOrientationZ().x local CargoZY = Cargo:GetOrientationZ().y local CargoZZ = Cargo:GetOrientationZ().z -- Offset vector: 24 m ahead, 5 meters above, 0 meters starboard (variable format) local Offset_X = 24 local Offset_Y = 5 local Offset_Z = 0 -- I've set it to 0 because the cargo containers are aligned with the ship's Z origin -- Scale components (variable format) local Scale_XX = CargoXX * Offset_X local Scale_XY = CargoXY * Offset_X local Scale_XZ = CargoXZ * Offset_X local Scale_YX = CargoYX * Offset_Y local Scale_YY = CargoYY * Offset_Y local Scale_YZ = CargoYZ * Offset_Y local Scale_ZX = CargoZX * Offset_Z local Scale_ZY = CargoZY * Offset_Z local Scale_ZZ = CargoZZ * Offset_Z -- Add up the relevant scale components to get the final offset values local Addition_X = Scale_XX + Scale_YX + Scale_ZX local Addition_Y = Scale_XY + Scale_YY + Scale_ZY local Addition_Z = Scale_XZ + Scale_YZ + Scale_ZZ -- Get PointVec3 and add up vectors in the unit coordinate system ==> this gives the offset vector relative the the origin of the map (variable format) local Cargo_Offset_PointVec3 = Cargo:GetPointVec3():AddX(Addition_X):AddY(Addition_Y):AddZ(Addition_Z) -- Flare Cargo_Offset_PointVec3:FlareRed() end Edited June 3, 2021 by Hardcard 1 [sIGPIC][/sIGPIC] Link to comment Share on other sites More sharing options...
toutenglisse Posted June 3, 2021 Share Posted June 3, 2021 6 hours ago, GusPT said: ... transform position to a place point between 9 and 3' o clock in front of the reference unit Hi, as a supplementary option, here is code I use to do that, just slightly modified to use your terms and values (so not tested but should work, "positionVec3" is a point placed 4 to 5 km away in front of "reference_unit", and between its 9 to 3 o'clock) : Spoiler local refPoint = reference_unit.getPoint() local dir1 = mist.getHeading(reference_unit) local dir3 = mist.utils.round(dir1, 1) repeat unitSpawnPoint = mist.getRandPointInCircle(refPoint, 5000, 4000) positionVec3 = mist.utils.makeVec3GL(unitSpawnPoint) -- mist.utils.makeVec3(unitSpawnPoint, refPoint.y) if you want point at reference_unit's altitude instead of ground level vec = {x = positionVec3.x - refPoint.x, y = positionVec3.y - refPoint.y, z = positionVec3.z - refPoint.z} dir4 = mist.utils.getDir(vec, refPoint) dir2 = mist.utils.round(dir4, 1) until dir2 < dir3 + 1.57 and dir2 > dir3 - 1.57 1 Link to comment Share on other sites More sharing options...
GusPT Posted June 3, 2021 Author Share Posted June 3, 2021 Thanks for the quick responses guys. If I understand correctly @Hardcard approach is deterministic while @toutenglisse tries to get a position within the angle restrictions, which might have a performance impact for what I want to do. However both approaches are useful and come to think of it, I can probably extract the mist.getRandPointInCircle code (also looking for some randomness here for the radius) and change it to limit it to the angles I'm looking for. Then transform the result to a vec3 using mist.utils.makeVec3. Wish I had paid more attention to my algebra classes.. I'll post back the results when I'm done. Link to comment Share on other sites More sharing options...
Hardcard Posted June 3, 2021 Share Posted June 3, 2021 (edited) @GusPT Doesn't need to be deterministic, you can randomize the offsets at your convenience, ofc. As long as the x offset is a positive number, the spawn point will be ahead of the chosen aircraft (regardless of its orientation). As for the z offset, it can be either positive (right side relative to aircraft) or negative (left side relative to aircraft). Y offset is for altitude, + = above, - = below. The offset point doesn't even have to be the actual spawn point, you can use it as the center of a spawn zone instead (from which you can get a random spawn point). Think of it like a big ass Cartesian graph, with your aircraft at the origin. 12 o'clock? x = positive number, z = 0 9 o'clock? x = 0, z = negative number 3 o'clock? x = 0, z = positive number 45º right? x = z ( as long as the value is greater than 0 ) 45º left? z = x * -1 ( x needs to be a positive number greater than 0 ) etc. Edited June 3, 2021 by Hardcard [sIGPIC][/sIGPIC] Link to comment Share on other sites More sharing options...
Grimes Posted June 3, 2021 Share Posted June 3, 2021 (edited) Ah crap. I apparently forgot to update the documentation. mist.getRandPointInCircle has the ability to limit the range of angles used to generate a point since 2017. So you can make the possible area pacman shaped if you wanted to. Should be something like this. local u = Unit.getByName('whatever') local heading = mist.getHeading(u, true) local headingDeg = math.deg(heading) local newPoint = mist.getRandPointInCircle(u:getPoint(), 20000, 10000, headingDeg +90, headingDeg - 90) Might have to switch the headingDeg values since I kinda forgot how its supposed to work. Big oof. Edit; updated the wiki documentation and confirmed that the above example is correct. Edited June 3, 2021 by Grimes New information has come to light man 1 2 The right man in the wrong place makes all the difference in the world. Current Projects: Grayflag Server, Scripting Wiki Useful Links: Mission Scripting Tools MIST-(GitHub) MIST-(Thread) SLMOD, Wiki wishlist, Mission Editing Wiki!, Mission Building Forum Link to comment Share on other sites More sharing options...
toutenglisse Posted June 4, 2021 Share Posted June 4, 2021 1 hour ago, Grimes said: ... Edit; updated the wiki documentation and confirmed that the above example is correct. ... Thanks ! It simplifies a lot. Link to comment Share on other sites More sharing options...
GusPT Posted June 4, 2021 Author Share Posted June 4, 2021 @Hardcard absolutely. I meant deterministic in the sense that there are no retries, just need to input the proper values. Perhaps I chose the wrong word. @Grimes I've been using mist 4.3.74, didn't even know there was a new version, thought the project was dead and replaced by Moose. Good stuff!! Will have a look to see what else is new, but it seems this version does exactly what I want. Thanks! Link to comment Share on other sites More sharing options...
Grimes Posted June 4, 2021 Share Posted June 4, 2021 Not dead, but certainly slowed down. I'm rather content with it being the lightweight option and have always preferred adding other scripts that use it to handle specific things like CTLD, my old IADScript, and others. Doesn't help that DCS patches aren't exactly a treasure trove of new scripting functions, so there isn't a constant need to add functionality. I'll typically add stuff whenever I delve into mission making as I'll end up making something useful that could be adapted for mist. The functions added back in November are a result of that for example. I also have a habit of only using the development branch on github and only merge it to the main branch rarely. The right man in the wrong place makes all the difference in the world. Current Projects: Grayflag Server, Scripting Wiki Useful Links: Mission Scripting Tools MIST-(GitHub) MIST-(Thread) SLMOD, Wiki wishlist, Mission Editing Wiki!, Mission Building Forum Link to comment Share on other sites More sharing options...
GusPT Posted June 5, 2021 Author Share Posted June 5, 2021 (edited) Totally agree. I've been kept using Mist due to its lightweight, MOOSE is too cumbersome for the most stuff I've been working on. It's nice to know Mist we'll be still be around for some time. Thanks for your work @Grimes edit: BTW, the new parameters work great! Edited June 5, 2021 by GusPT Feedback on new getRandPointInCircle Link to comment Share on other sites More sharing options...
Recommended Posts