/* ----------------------------------------------------------------------------- This source file is part of OpenSpace3D For the latest info, see http://www.openspace3d.com Copyright (c) 2012 I-maginer This program is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA, or go to http://www.gnu.org/copyleft/lesser.txt ----------------------------------------------------------------------------- */ var OCULUS_HAND_MODEL = 0;; struct ObjCtlOxrStr = [ POBJOXRCTL_id : I, POBJOXRCTL_sName : S, POBJOXRCTL_obj : SO3_OBJECT, POBJOXRCTL_defObj : SO3_OBJECT, POBJOXRCTL_body : SO3_PHYSICBODY, POBJOXRCTL_objTrigger : SO3_OBJECT, POBJOXRCTL_objTrackPip : SO3_OBJECT, POBJOXRCTL_lBones : [[SO3_OBJECT [F F F F] I] r1], POBJOXRCTL_lBtnState : [I r1], POBJOXRCTL_lTouchState : [I r1], POBJOXRCTL_lAxis : [F F F F], POBJOXRCTL_iMode : I, POBJOXRCTL_initPos : [[F F F] [F F F F]], POBJOXRCTL_bState : I, POBJOXRCTL_bRayState : I, POBJOXRCTL_fRumbleVal : F, POBJOXRCTL_iRumbleTime : I, POBJOXRCTL_iRumbleDuration : I, POBJOXRCTL_pGrabBody : SO3_PHYSICBODY, POBJOXRCTL_pGrabJoint : SO3_PHYSICCONTRAINT, POBJOXRCTL_pGrabbedBody : SO3_PHYSICBODY, POBJOXRCTL_bGrab : I, POBJOXRCTL_oPointerSrc : SO3_OBJECT, POBJOXRCTL_oPointer : SO3_OBJECT, POBJOXRCTL_oRayDummy : SO3_OBJECT, POBJOXRCTL_oRay1 : SO3_OBJECT, POBJOXRCTL_oRay2 : SO3_OBJECT, POBJOXRCTL_oTarget : SO3_OBJECT, POBJOXRCTL_matRay : SO3_MATERIAL, POBJOXRCTL_bRayVisible : I, POBJOXRCTL_fLastWheel : F, POBJOXRCTL_fLastVel : [F F F], POBJOXRCTL_fLastOmega : [F F F], POBJOXRCTL_vOffset : [[F F F] [F F F F]], POBJOXRCTL_vDefOffset : [[F F F] [F F F F]], POBJOXRCTL_bObjChanged : I, POBJOXRCTL_iTeleportState : I, POBJOXRCTL_iLastAutoClick : I, POBJOXRCTL_bIsHand : I ]mkObjCtlOxrStr;; struct ObjOpenXrStr = [ POXR_inst : PInstance, POXR_sGroupName : S, POXR_device : ObjOpenXr, POXR_bHandTracking : I, POXR_bPassthrough : I, POXR_controllers : [ObjCtlOxrStr r1], POXR_tLastYPR : [F F F], POXR_tLastPos : [F F F], POXR_tPrevHeadPos : [[F F F] [F F F F]], POXR_bConnected : I, POXR_iFrameAcc : I, POXR_iNbFrame : I, POXR_lostTick : I, POXR_wTimer : Timer, POXR_bUseInitialPos : I, POXR_bControl : I, POXR_bOrientation : I, POXR_bPosition : I, POXR_bLeftControl : I, POXR_bLeftOrientation : I, POXR_bLeftPosition : I, POXR_bLeftTrigger : I, POXR_bLeftGrip : I, POXR_bLeftStick : I, POXR_bRightControl : I, POXR_bRightOrientation : I, POXR_bRightPosition : I, POXR_bRightTrigger : I, POXR_bRightGrip : I, POXR_bRightStick : I, POXR_bIgnoreControllerPhysics : I, POXR_bCurrentMouseRay : I, POXR_bVisible : I, POXR_bLastUpdateMode : I, POXR_bCtrlState : I, POXR_iShowRay : I, POXR_iShowRayMode : I, POXR_iTeleportMode : I, POXR_iTeleportController : I, POXR_iTeleportCur : I, POXR_bAutoClick : I, POXR_fAutoClickDist : F, POXR_fScaleRatio : F ]mkObjOpenXrStr;; proto stopStereo = fun [ObjOpenXrStr] I;; var BtnA = 0;; var BtnB = 1;; var BtnRThumb = 2;; var BtnX = 3;; var BtnY = 4;; var BtnLThumb = 5;; var BtnGrip = 6;; var BtnTrigger = 7;; var BtnMenu = 8;; var BtnBack = 9;; var TouchThumbUp = 6;; var TouchPointing = 8;; fun cbShowRay(inst, from, action, param, reply, obstr)= set obstr.POXR_iShowRay = 1; 0;; fun cbHideRay(inst, from, action, param, reply, obstr)= if (obstr.POXR_iShowRayMode != 2) then set obstr.POXR_iShowRay = 0 else set obstr.POXR_iShowRay = 2; 0;; fun cbSetTeleportMode(inst, from, action, param, reply, obstr)= if (param == nil) then nil else set obstr.POXR_iTeleportMode = atoi param; 0;; fun getControllerTrigger(parent)= let SO3ObjectGetChildren parent -> sons in let nil -> found in ( while (sons != nil && found == nil) do ( let hd sons -> obj in let SO3ObjectGetName obj -> name in if ((strfind "trigger" name 0) == nil) then set found = getControllerTrigger obj else set found = obj; set sons = tl sons; ); found; );; fun getControllerTrack(parent)= let SO3ObjectGetChildren parent -> sons in let nil -> found in ( while (sons != nil && found == nil) do ( let hd sons -> obj in let SO3ObjectGetName obj -> name in if ((strfind "track_pip" name 0) == nil) then set found = getControllerTrack obj else set found = obj; set sons = tl sons; ); found; );; fun isCollideBody(body)= if ((SO3BodyGetType body) & 1) then 1 else 0;; fun isAnInvalidBody(obstr, ctrlstr, pos, body)= let SO3BodyGetMassMatrix body -> [mass _] in let SO3PhysicsGetMaterialName (SO3BodyGetMaterial body) -> bmat in if ((!strcmp bmat "nograb") || (!strcmp bmat "ignore") || /*(mass == 0.0) ||*/ ((SO3BodyGetType body) & 4) || (SO3BodyGetIgnoreCollision body) || (body == (SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj)) || (isCollideBody body) || (SO3BodyGetFluid body)) && (!(SO3BodyGetType body) & 2) then ( 1; ) else let 0 -> res in ( let 0 -> i in let sizelist obstr.POXR_controllers -> size in while (i < size) do ( let nth_list obstr.POXR_controllers i -> sctrlstr in if ((sctrlstr.POBJOXRCTL_body == body) || (sctrlstr.POBJOXRCTL_pGrabBody == body)) then set res = 1; set i = i + 1; ); res; );; fun isAnInvalidTeleportBody(obstr, ctrlstr, pos, body)= let if pos == 0 then 1 else 0 -> i in let nth_list obstr.POXR_controllers i -> sctrlstr in let SO3PhysicsGetMaterialName (SO3BodyGetMaterial body) -> bmat in if ((!strcmp bmat "nonav") || (!strcmp bmat "ignore") || (SO3BodyGetIgnoreCollision body) || (body == (SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj)) || (isCollideBody body) || (SO3BodyGetFluid body) || (sctrlstr.POBJOXRCTL_body == body) || (sctrlstr.POBJOXRCTL_pGrabBody == body) || (sctrlstr.POBJOXRCTL_pGrabbedBody == body)) then 1 else 0;; fun getValidRay(lray, obstr, ctrlstr, pos, cbtest)= let nil -> body in let 0.0 -> dist in let [0.0 1.0 0.0] -> normal in ( while ((lray != nil) && (body == nil)) do ( let hd lray -> [tbody tdist tnormal] in if (exec cbtest with [obstr ctrlstr pos tbody]) then nil else ( set body = tbody; set dist = tdist; set normal = tnormal; ); set lray = tl lray; ); [body dist normal] );; fun resetBodiesSimulation(l)= if l == nil then nil else let hd l -> obj in let SO3SceneNodeGetBody obj -> body in ( SO3BodySetVelocity body [0.0 0.0 0.0]; SO3BodySetOmega body [0.0 0.0 0.0]; //force physic body to obj pos if ((SO3SceneNodeGetBody obj) == nil) then nil else ( SO3ObjectSetPosition obj SO3ObjectGetPosition obj; SO3ObjectSetOrientation obj SO3ObjectGetOrientation obj; ); resetBodiesSimulation SO3GetRootBonesFromMesh obj; resetBodiesSimulation (SO3ObjectGetChildren obj); resetBodiesSimulation (tl l); ); 0;; fun setObjectRenderQueue(l, queue, sons)= if l == nil then nil else let hd l -> obj in ( if (!sons) then nil else setObjectRenderQueue (SO3ObjectGetChildren obj) queue sons; SO3ObjectSetRenderQueue obj queue; setObjectRenderQueue (tl l) queue sons; ); 0;; fun setObjectVisibility(l, state, sons)= if l == nil then nil else let hd l -> obj in ( if (!sons) then nil else setObjectVisibility (SO3ObjectGetChildren obj) state sons; if ((SO3ObjectGetType obj) == SO3_TYPE_LIGHT) then nil else SO3ObjectSetVisible obj state 0; setObjectVisibility (tl l) state sons; ); 0;; fun setObjectControlerFlags(l, flag, state, sons)= if l == nil then nil else let hd l -> obj in ( if (!sons) then nil else setObjectControlerFlags (SO3ObjectGetChildren obj) flag state sons; if (state) then SO3ObjectSetFlags obj (SO3ObjectGetFlags obj) | flag else SO3ObjectSetFlags obj (SO3ObjectGetFlags obj) & ~flag; setObjectControlerFlags (tl l) flag state sons; ); 0;; fun cbOpenXrPreRenderCam(inst, sessionstr, etime, obstr)= _UpdateOpenXr obstr.POXR_device; let sessionstr.V3D_sessionView -> viewstr in let V3DgetDefaultViewport (V3DgetSessionView c3dXsession) -> viewportstr in let V3DgetObjectByName c3dXsession "Current camera" -> camera in if !(_GetOpenXrVisibility obstr.POXR_device) then ( if (obstr.POXR_bUseInitialPos) then nil else ( set obstr.POXR_tLastPos = nil; set obstr.POXR_tLastYPR = nil; ); set obstr.POXR_bVisible = 0; let sizelist obstr.POXR_controllers -> size in let 0 -> i in while (i < size) do ( //OPENVR_CONTROLLER_LEFT OPENVR_CONTROLLER_RIGHT let nth_list obstr.POXR_controllers i -> ctrlstr in ( set ctrlstr.POBJOXRCTL_fLastVel = [0.0 0.0 0.0]; set ctrlstr.POBJOXRCTL_fLastOmega = [0.0 0.0 0.0]; if (ctrlstr.POBJOXRCTL_pGrabbedBody == nil) then nil else ( SO3BodySetVelocity ctrlstr.POBJOXRCTL_pGrabbedBody [0.0 0.0 0.0]; SO3BodySetOmega ctrlstr.POBJOXRCTL_pGrabbedBody [0.0 0.0 0.0]; ); SO3BodySetVelocity SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj [0.0 0.0 0.0]; SO3BodySetOmega SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj [0.0 0.0 0.0]; ); set i = i + 1; ); 0; ) else ( let SO3CameraGetNearClipDistance camera -> nearclip in let SO3CameraGetFarClipDistance camera -> farclip in let _GetOpenXrProjectionMatrix obstr.POXR_device nearclip farclip -> pmat in if (pmat == nil) then nil else let pmat -> [lmat rmat] in SO3BufferSetStereoProjectionMatrix sessionstr.V3D_sessionView.V3D_buffer lmat rmat 1; SO3BufferSetStereoEyeSpacing viewstr.V3D_buffer (_GetOpenXrIPD obstr.POXR_device); //skip first sent pos if (!obstr.POXR_bVisible) then ( //first hmd pos can be negative on initialisation ? let _GetOpenXrPosition obstr.POXR_device -> [_ hmdheight _] in if (hmdheight <. 0.0) then nil else ( set obstr.POXR_bVisible = 1; set obstr.POXR_bLastUpdateMode = 1; ); ) else ( let _GetOpenXrOrientation obstr.POXR_device -> quat in let _GetOpenXrPosition obstr.POXR_device -> pos in let SO3ObjectGetParent SO3ObjectGetParent camera -> dcam in //neckdummy //let SO3ObjectGetGlobalOrientation dcam -> oquat in let SO3ObjectGetPosition dcam -> [_ camheight _] in let pos -> [hmdx hmdheight hmdy] in let SO3MathsQuatToEulerDegreePYR quat -> [pitch yaw roll] in let quatInverse SO3MathsEulerPYRToQuat (let SO3MathsQuatToEulerPYR quat -> [_ ydir _] in [0.0 ydir 0.0]) -> dirquat in ( if (quat == nil || pos == nil) then nil else ( let if (obstr.POXR_tLastPos == nil) then if (obstr.POXR_bUseInitialPos) then SO3MathsQuatGetDirection dirquat [hmdx 0.0 hmdy] else [0.0 0.0 0.0] else SO3MathsQuatGetDirection dirquat (subVectorF pos obstr.POXR_tLastPos) -> [px _ pz] in let hmdheight -> py in ( let if (obstr.POXR_tLastYPR == nil) then if (obstr.POXR_bUseInitialPos) then yaw else 0.0 else let obstr.POXR_tLastYPR -> [ly _ _] in yaw -. ly -> ryaw in let if ryaw >. 180.0 then ryaw -. 360.0 else if ryaw <. (-.180.0) then ryaw +. 360.0 else ryaw -> ryaw in if (!obstr.POXR_bControl) then nil else ( let ftoa pitch -> sax in let ftoa ryaw -> say in let ftoa roll -> saz in SendPluginEvent obstr.POXR_inst "Control" (strcatn (ftoa px)::" "::(ftoa py)::" "::(ftoa pz)::"\n"::sax::" "::say::" "::saz::"\n3"::nil) obstr.POXR_inst.INST_sName; if (obstr.POXR_bLastUpdateMode != 1) then nil else set obstr.POXR_bLastUpdateMode = 2; ); ); if (!obstr.POXR_bOrientation) then nil else SendPluginEvent obstr.POXR_inst "Orientation" (strcatn (ftoa pitch)::" "::(ftoa yaw)::" "::(ftoa roll)::nil) obstr.POXR_inst.INST_sName; set obstr.POXR_tLastYPR = [yaw pitch roll]; if (!obstr.POXR_bPosition) then nil else let pos -> [px py pz] in SendPluginEvent obstr.POXR_inst "Position" (strcatn (ftoa px)::" "::(ftoa py)::" "::(ftoa pz)::nil) obstr.POXR_inst.INST_sName; set obstr.POXR_tLastPos = pos; ); ); 0; ); );; fun cbOpenXrPreRender(inst, viewstr, obstr)= let V3DgetDefaultViewport (V3DgetSessionView c3dXsession) -> viewportstr in if (!obstr.POXR_bVisible) then nil else ( let _GetOpenXrOrientation obstr.POXR_device -> quat in let _GetOpenXrPosition obstr.POXR_device -> pos in let V3DgetObjectByName c3dXsession "Current camera" -> camera in let SO3ObjectGetParent SO3ObjectGetParent camera -> dcam in //neckdummy //let SO3ObjectGetGlobalOrientation dcam -> oquat in let SO3ObjectGetPosition dcam -> [_ camheight _] in let pos -> [_ hmdheight _] in ( if ((quat == nil || pos == nil) || !obstr.POXR_bCtrlState) then nil else ( let SO3ObjectGetGlobalPosition dcam -> [spx spy spz] in let [spx (spy -. camheight) spz] -> spos in let SO3ObjectGetGlobalOrientation dcam -> bodyquat in let SO3MathsQuatToEulerPYR quat -> [_ ryaw _ ] in let SO3MathsEulerPYRToQuat [0.0 ryaw 0.0] -> hquat in let SO3MathsQuatDiff bodyquat hquat -> qdiff in let SO3MathsQuatGetDirection qdiff pos -> [hx hy hz] in let subVectorF spos [hx 0.0 hz] -> feetpos in let subVectorF [spx spy spz] [hx 0.0 hz] -> headpos in let if (obstr.POXR_tPrevHeadPos == nil) then [1 2.0] else let obstr.POXR_tPrevHeadPos -> [phpos phquat] in let getVectorLengthF (subVectorF headpos phpos) -> lm in let SO3MathsQuatDiff bodyquat phquat -> qrot in if ((lm >. 0.10) || ((getVector4LengthF qrot) >. 1.0)) then [1 lm] else [0 lm] -> [teleporting teleportlenght] in let nil -> cursorpos in ( set obstr.POXR_tPrevHeadPos = [headpos bodyquat]; let 0 -> i in //Hack to force left / right update concurrency. if left controller is linked to right one, force update order in that case let 0 -> doagain in let sizelist obstr.POXR_controllers -> size in while (i < size) do ( //OPENVR_CONTROLLER_LEFT OPENVR_CONTROLLER_RIGHT let nth_list obstr.POXR_controllers i -> ctrlstr in let strcatn obstr.POXR_inst.INST_sName::"ctrl_"::(itoa i)::nil -> evtid in let SO3VirtualPointerGetId ctrlstr.POBJOXRCTL_oPointer -> pid in ( let _GetOpenXrControllerVisibility obstr.POXR_device i -> cstate in let if (cstate == nil) then 0 else cstate -> cstate in ( if (cstate == ctrlstr.POBJOXRCTL_bState) then nil else ( let if (cstate == 1) then strcat ctrlstr.POBJOXRCTL_sName " found" else strcat ctrlstr.POBJOXRCTL_sName " lost" -> ename in ( //addLogMessage ename; SendPluginEvent obstr.POXR_inst ename nil nil; ); set ctrlstr.POBJOXRCTL_bState = cstate; if (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj) then nil else setObjectVisibility ctrlstr.POBJOXRCTL_obj::nil cstate 1; ); let ctrlstr.POBJOXRCTL_vOffset -> [offsetpos offsetquat] in let _GetOpenXrControllerPosition obstr.POXR_device i -> cpos in let _GetOpenXrControllerOrientation obstr.POXR_device i -> cquat in let SO3MathsQuatAdd qdiff cquat -> ctloquat in let addVectorF (SO3MathsQuatGetDirection ctloquat offsetpos) addVectorF addVectorF feetpos (SO3MathsQuatGetDirection qdiff cpos) [0.0 (camheight -. hmdheight) 0.0] -> ctlpos in let SO3MathsQuatAdd ctloquat offsetquat -> ctlquat in // apply offset let nil -> np3d in let nil -> nobflag in ( if (!ctrlstr.POBJOXRCTL_bState) then ( set ctrlstr.POBJOXRCTL_fLastVel = [0.0 0.0 0.0]; set ctrlstr.POBJOXRCTL_fLastOmega = [0.0 0.0 0.0]; if (ctrlstr.POBJOXRCTL_pGrabbedBody == nil) then nil else ( SO3BodySetVelocity ctrlstr.POBJOXRCTL_pGrabbedBody [0.0 0.0 0.0]; SO3BodySetOmega ctrlstr.POBJOXRCTL_pGrabbedBody [0.0 0.0 0.0]; ); SO3BodySetVelocity SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj [0.0 0.0 0.0]; SO3BodySetOmega SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj [0.0 0.0 0.0]; 0; ) else ( let SO3MathsQuatGetDirection qdiff _GetOpenXrControllerVelocity obstr.POXR_device i -> vel in let SO3MathsQuatGetDirection qdiff _GetOpenXrControllerAngularVelocity obstr.POXR_device i -> omega in ( set ctrlstr.POBJOXRCTL_fLastVel = vel; set ctrlstr.POBJOXRCTL_fLastOmega = omega; ); if (ctrlstr.POBJOXRCTL_obj == nil) then nil else ( //update defbody anyway if (ctrlstr.POBJOXRCTL_obj == ctrlstr.POBJOXRCTL_defObj) then nil else ( if (cpos == nil) then nil else SO3ObjectSetGlobalPosition ctrlstr.POBJOXRCTL_defObj ctlpos; if (cquat == nil) then nil else SO3ObjectSetGlobalOrientation ctrlstr.POBJOXRCTL_defObj ctlquat; ); let SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj -> curbody in let SO3BodyGetMassMatrix curbody -> [cmass _] in let (obstr.POXR_bIgnoreControllerPhysics && (ctrlstr.POBJOXRCTL_pGrabbedBody == nil) && (ctrlstr.POBJOXRCTL_obj == ctrlstr.POBJOXRCTL_defObj)) -> defobstate in if (ctrlstr.POBJOXRCTL_bObjChanged || !(V3DphysGetState c3dXsession) || (curbody == nil) || (cmass == 0.0) || (teleporting && (ctrlstr.POBJOXRCTL_pGrabbedBody == nil)) || defobstate) then ( if (cpos == nil) then nil else SO3ObjectSetGlobalPosition ctrlstr.POBJOXRCTL_obj ctlpos; if (cquat == nil) then nil else SO3ObjectSetGlobalOrientation ctrlstr.POBJOXRCTL_obj ctlquat; //if (ctrlstr.POBJOXRCTL_pGrabbedBody != nil) then nil else resetBodiesSimulation ctrlstr.POBJOXRCTL_obj::nil; set ctrlstr.POBJOXRCTL_bObjChanged = 0; if (i == 0) then nil else set doagain = doagain + 1; 0; ) else ( //Teleport grabbed obj let SO3BodyGetMassMatrix ctrlstr.POBJOXRCTL_pGrabbedBody -> [gbmass _] in if (doagain || !teleporting || (ctrlstr.POBJOXRCTL_pGrabbedBody == nil) || (gbmass >. (cmass *. 5.0))) then nil else ( SO3BodySetVelocity ctrlstr.POBJOXRCTL_pGrabbedBody [0.0 0.0 0.0]; SO3BodySetOmega ctrlstr.POBJOXRCTL_pGrabbedBody [0.0 0.0 0.0]; let SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_obj -> gcpos in let SO3ObjectGetGlobalPosition (SO3BodyGetSceneNode ctrlstr.POBJOXRCTL_pGrabbedBody) -> gbpos in let addVectorF ctlpos (subVectorF gbpos gcpos) -> nbpos in SO3BodyMoveTo ctrlstr.POBJOXRCTL_pGrabbedBody nbpos 0.6; ); // if the body father have a body we limits the stiffness let SO3SceneNodeGetBody (SO3ObjectGetParent ctrlstr.POBJOXRCTL_obj) -> pbody in let SO3BodyGetMassMatrix pbody -> [pmass _] in let if ((pbody != nil) && (pmass >. 0.0)) then [0.1 0.3] else [0.8 0.8] -> [stiffm stiffr] in ( SO3BodyMoveTo curbody ctlpos stiffm; SO3BodyRotateTo curbody ctlquat stiffr; ); 0; ); //update hand bones let _GetOpenXrControllerType obstr.POXR_device i -> ctype in let if (ctype == 1) then 1 else 0 -> ishand in if (ishand == ctrlstr.POBJOXRCTL_bIsHand) then nil else ( set ctrlstr.POBJOXRCTL_bIsHand = ishand; //reset bones rotation if (ishand) then nil else ( let sizelist ctrlstr.POBJOXRCTL_lBones -> lbsize in let 0 -> bi in while (bi < lbsize) do ( let nth_list ctrlstr.POBJOXRCTL_lBones bi -> [b offq id] in SO3ObjectSetOrientation b offq; set bi = bi + 1; ); ); let if (ishand) then strcat ctrlstr.POBJOXRCTL_sName " is hand" else strcat ctrlstr.POBJOXRCTL_sName " is controller" -> ename in SendPluginEvent obstr.POXR_inst ename nil nil; ); if (ctrlstr.POBJOXRCTL_bIsHand != 1) then nil else ( let _GetOpenXrControllerBonesRotation obstr.POXR_device i -> lquat in let sizelist ctrlstr.POBJOXRCTL_lBones -> lbsize in let 0 -> bi in while (bi < lbsize) do ( let nth_list ctrlstr.POBJOXRCTL_lBones bi -> [b offq id] in let nth_list lquat id -> bq in if (OCULUS_HAND_MODEL) then let bq -> [bqx bqy bqz bqw] in SO3ObjectSetOrientation b [if (i == 1) then (-.bqy) else bqy bqx if (i == 0) then (-.bqy) else bqy bqw] else SO3ObjectSetOrientation b bq; set bi = bi + 1; ); ); ); let if (i == 0) then obstr.POXR_bLeftOrientation else if (i == 1) then obstr.POXR_bRightOrientation else 1 -> oenable in let strcat ctrlstr.POBJOXRCTL_sName " orientation" -> ename in if (!oenable) then nil else let SO3MathsQuatToEulerDegreePYR ctlquat -> [pitch yaw roll] in SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa pitch)::" "::(ftoa yaw)::" "::(ftoa roll)::nil) evtid; let if (i == 0) then obstr.POXR_bLeftPosition else if (i == 1) then obstr.POXR_bRightPosition else 1 -> oenable in let strcat ctrlstr.POBJOXRCTL_sName " position" -> ename in if (!oenable) then nil else let ctlpos -> [cx cy cz] in SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa cx)::" "::(ftoa cy)::" "::(ftoa cz)::nil) evtid; 0; ); let _GetOpenXrControllerAxis obstr.POXR_device i -> [padx pady triggerz gripw] in let _GetOpenXrControllerButtons obstr.POXR_device i -> lbuttons in let _GetOpenXrControllerTouches obstr.POXR_device i -> ltouches in ( let if (i == 0) then BtnLThumb else BtnRThumb -> ibtn in let nth_list ctrlstr.POBJOXRCTL_lBtnState ibtn -> pBtn in let nth_list lbuttons ibtn -> nBtn in ( if (pBtn == nBtn) then nil else ( let if (nBtn == 1) then strcat ctrlstr.POBJOXRCTL_sName " thumb down" else strcat ctrlstr.POBJOXRCTL_sName " thumb up" -> ename in SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa padx)::" "::(ftoa pady)::nil) evtid; /*if (!ctrlstr.POBJOXRCTL_bIsHand) then nil else ( //Teleport only for pad mode and current or both controller if ((obstr.POXR_iTeleportMode != 1) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i)) || ((obstr.POXR_iTeleportCur != nil) && (obstr.POXR_iTeleportCur != i))) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = if nBtn then 1 else 3; set obstr.POXR_iTeleportCur = i; ); );*/ ); if (!ctrlstr.POBJOXRCTL_bIsHand || (obstr.POXR_iTeleportMode != 2) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i)) || ((obstr.POXR_iTeleportCur != nil) && (obstr.POXR_iTeleportCur != i))) then nil else ( let nth_list ctrlstr.POBJOXRCTL_lBtnState BtnGrip -> gBtn in let nth_list lbuttons BtnTrigger -> tBtn in let nth_list lbuttons if (i == 0) then BtnA else BtnX -> aBtn in let nth_list lbuttons if (i == 0) then BtnB else BtnY -> bBtn in if (gBtn || tBtn || aBtn || bBtn) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = nBtn; set obstr.POXR_iTeleportCur = if nBtn then i else nil; ); ); ); let if (i == 0) then BtnLThumb else BtnRThumb -> ibtn in let nth_list ctrlstr.POBJOXRCTL_lTouchState ibtn -> pTouch in let nth_list ltouches ibtn -> nTouch in ( if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName " stick touch" else strcat ctrlstr.POBJOXRCTL_sName " stick untouch" -> ename in //Teleport only for pad mode and current or both controller if ((obstr.POXR_iTeleportMode != 1) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i)) || ((obstr.POXR_iTeleportCur != nil) && (obstr.POXR_iTeleportCur != i))) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = if nTouch then 1 else 3; set obstr.POXR_iTeleportCur = i; ); ); if (ctrlstr.POBJOXRCTL_bIsHand || (obstr.POXR_iTeleportMode != 2) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i)) || ((obstr.POXR_iTeleportCur != nil) && (obstr.POXR_iTeleportCur != i))) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = nTouch; set obstr.POXR_iTeleportCur = if nTouch then i else nil; ); let if (i == 0) then obstr.POXR_bLeftControl else if (i == 1) then obstr.POXR_bRightControl else 1 -> oenable in let strcat ctrlstr.POBJOXRCTL_sName " control" -> ename in if (!oenable) then ( SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa 0.0)::" "::(ftoa 0.0)::" "::(ftoa 0.0)::nil) evtid ) else ( if (absf padx) >. (absf pady) then SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa padx)::" "::(ftoa 0.0)::" "::(ftoa 0.0)::nil) evtid else SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa 0.0)::" "::(ftoa 0.0)::" "::(ftoa (-.pady))::nil) evtid; ); //if (obstr.POXR_bCurrentMouseRay != i) then nil else ( if ((ctrlstr.POBJOXRCTL_fLastWheel == nil) || (pady == 0.0) )then nil else SO3VirtualPointerSendWheel ctrlstr.POBJOXRCTL_oPointer (ftoi ((pady -. ctrlstr.POBJOXRCTL_fLastWheel) *. 60.0)); ); set ctrlstr.POBJOXRCTL_fLastWheel = if (pady == 0.0) then nil else pady; ); let if (i == 0) then obstr.POXR_bLeftStick else if (i == 1) then obstr.POXR_bRightStick else 1 -> oenable in let strcat ctrlstr.POBJOXRCTL_sName " stick" -> ename in if (!oenable) then nil else SendPluginEvent obstr.POXR_inst ename (strcatn (ftoa padx)::" "::(ftoa pady)::nil) evtid; let if (i == 0) then obstr.POXR_bLeftTrigger else if (i == 1) then obstr.POXR_bRightTrigger else 1 -> oenable in let strcat ctrlstr.POBJOXRCTL_sName " trigger value" -> ename in if (!oenable) then nil else SendPluginEvent obstr.POXR_inst ename (ftoa triggerz) evtid; let if (i == 0) then obstr.POXR_bLeftGrip else if (i == 1) then obstr.POXR_bRightGrip else 1 -> oenable in let strcat ctrlstr.POBJOXRCTL_sName " grip value" -> ename in if (!oenable) then nil else SendPluginEvent obstr.POXR_inst ename (ftoa gripw) evtid; //update virtual pointer on widgets SO3VirtualPointerSetRayCastMode ctrlstr.POBJOXRCTL_oPointer if ((obstr.POXR_iShowRay == 1) || (ctrlstr.POBJOXRCTL_iTeleportState)) then 2 else 1; let SO3VirtualPointerGetEnable ctrlstr.POBJOXRCTL_oPointer -> vrptrstate in if (/*(obstr.POXR_bCurrentMouseRay != i) ||*/ !vrptrstate || !ctrlstr.POBJOXRCTL_bState || (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj)) then ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy 0 1; setObjectRenderQueue ctrlstr.POBJOXRCTL_defObj::nil 66 1; 0; ) else ( SO3VirtualPointerUpdate ctrlstr.POBJOXRCTL_oPointer; let SO3VirtualPointerHasWidgetUnder ctrlstr.POBJOXRCTL_oPointer -> foundwidget in ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy (cstate && (ctrlstr.POBJOXRCTL_bRayState) && ((obstr.POXR_iShowRay == 1) || ctrlstr.POBJOXRCTL_iTeleportState || ((obstr.POXR_iShowRay == 2) && foundwidget))) 1; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 0 0; //update data for mouse let SO3VirtualPointerGetRayInfos ctrlstr.POBJOXRCTL_oPointer -> [session obj mat subid p3d puv dist] in let dist -. 0.05 -> dist in let SO3ObjectGetFlags obj -> obflag in ( set np3d = p3d; set nobflag = obflag; set cursorpos = SO3ViewportGetPixelPositionFromWorldPos viewportstr.V3D_viewport p3d; let if (foundwidget) then 71 else 66 -> rdpriority in setObjectRenderQueue ctrlstr.POBJOXRCTL_defObj::nil rdpriority 1; //scale laser SO3ObjectSetGlobalScale ctrlstr.POBJOXRCTL_oRayDummy [1.0 1.0 (maxf 0.0 ((SO3VirtualPointerGetlength ctrlstr.POBJOXRCTL_oPointer) -. 0.04))]; let cursorpos -> [cx cy] in let (nth_list lbuttons BtnTrigger) || (nth_list lbuttons (if (i == 0) then BtnX else BtnA)) -> nBtn in ( cbV3DviewPointerUpdate viewstr pid [(SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointer) (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointer)] cx cy nBtn [obj mat subid p3d puv dist]; //control virtual pointer on widgets SO3VirtualPointerSendMove ctrlstr.POBJOXRCTL_oPointer nBtn; cbV3DPointerMove viewstr pid [(SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointer) (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointer)] cx cy nBtn [obj mat subid p3d puv dist]; let ctrlstr.POBJOXRCTL_iLastAutoClick -> lclick in if (!obstr.POXR_bAutoClick || (!(obflag & iNodeFlagClick) && !(obflag & iNodeFlagVUI) && !foundwidget)) then nil else if ((dist >. obstr.POXR_fAutoClickDist) || ((lclick != nil) && ((_tickcount - lclick) < 1000))) then ( if ((dist >. (obstr.POXR_fAutoClickDist +. 0.02)) && ((lclick != nil) && ((_tickcount - lclick) > 100))) then set ctrlstr.POBJOXRCTL_iLastAutoClick = nil else nil; ) else ( SO3VirtualPointerSendClick ctrlstr.POBJOXRCTL_oPointer 1; cbV3DviewPointerClick viewstr pid [(SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointer) (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointer)] cx cy 1 [obj mat subid p3d puv dist]; //vibrate set ctrlstr.POBJOXRCTL_fRumbleVal = 1.0; set ctrlstr.POBJOXRCTL_iRumbleDuration = 50; set ctrlstr.POBJOXRCTL_iRumbleTime = _tickcount; SO3VirtualPointerSendUnClick ctrlstr.POBJOXRCTL_oPointer 1; cbV3DviewPointerUnClick viewstr pid cx cy 1 [obj mat subid p3d puv dist]; set ctrlstr.POBJOXRCTL_iLastAutoClick = _tickcount; ); ); ); ); 0; ); //buttons if (lbuttons == nil) then nil else let ctrlstr.POBJOXRCTL_lBtnState -> lpbtn in ( let nth_list ctrlstr.POBJOXRCTL_lBtnState BtnMenu -> pBtn in let nth_list lbuttons BtnMenu -> nBtn in if (pBtn == nBtn) then nil else ( let if (nBtn == 1) then strcat ctrlstr.POBJOXRCTL_sName " menu down" else strcat ctrlstr.POBJOXRCTL_sName " menu up" -> ename in SendPluginEvent obstr.POXR_inst ename nil nil; ); let nth_list ctrlstr.POBJOXRCTL_lBtnState BtnGrip -> pBtn in let nth_list lbuttons BtnGrip -> nBtn in if (pBtn == nBtn) then nil else ( //control virtual pointer on widgets //if (obstr.POXR_bCurrentMouseRay != i) then nil else let SO3VirtualPointerGetRayInfos ctrlstr.POBJOXRCTL_oPointer -> [session obj mat subid p3d puv dist] in let dist -. 0.05 -> dist in ( let cursorpos -> [cx cy] in if (nBtn == 1) then ( SO3VirtualPointerSendClick ctrlstr.POBJOXRCTL_oPointer 2; cbV3DviewPointerClick viewstr pid [(SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointer) (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointer)] cx cy 2 [obj mat subid p3d puv dist]; ) else ( SO3VirtualPointerSendUnClick ctrlstr.POBJOXRCTL_oPointer 2; cbV3DviewPointerUnClick viewstr pid cx cy 2 [obj mat subid p3d puv dist]; ); ); let if (nBtn == 1) then strcat ctrlstr.POBJOXRCTL_sName " grip down" else strcat ctrlstr.POBJOXRCTL_sName " grip up" -> ename in SendPluginEvent obstr.POXR_inst ename nil nil; ); // grip touch up /* let nth_list ctrlstr.POBJOXRCTL_lTouchState BtnGrip -> pTouch in let nth_list ltouches BtnGrip -> nTouch in if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName " grip touch" else strcat ctrlstr.POBJOXRCTL_sName " grip untouch" -> ename in SendPluginEvent obstr.POXR_inst ename nil evtid; ); */ let if (i == 0) then BtnX else BtnA -> ibtn in ( let nth_list ctrlstr.POBJOXRCTL_lBtnState ibtn -> pBtn in let nth_list lbuttons ibtn -> nBtn in if (pBtn == nBtn) then nil else ( if (!ctrlstr.POBJOXRCTL_bState) then nil else ( let cursorpos -> [cx cy] in let SO3VirtualPointerGetRayInfos ctrlstr.POBJOXRCTL_oPointer -> [session obj mat subid p3d puv dist] in if (nBtn == 1) then ( SO3VirtualPointerSendClick ctrlstr.POBJOXRCTL_oPointer 1; if (((obstr.POXR_iTeleportMode == 2) && ctrlstr.POBJOXRCTL_iTeleportState) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i))) then nil else cbV3DviewPointerClick viewstr pid [(SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointer) (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointer)] cx cy 1 [obj mat subid p3d puv dist]; if ((obstr.POXR_iTeleportMode != 2) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i)) || ((obstr.POXR_iTeleportCur != nil) && (obstr.POXR_iTeleportCur != i))) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = ctrlstr.POBJOXRCTL_iTeleportState + 2; set obstr.POXR_iTeleportCur = i; ); 0; ) else ( SO3VirtualPointerSendUnClick ctrlstr.POBJOXRCTL_oPointer 1; if (((obstr.POXR_iTeleportMode == 2) && ctrlstr.POBJOXRCTL_iTeleportState) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i))) then nil else cbV3DviewPointerUnClick viewstr pid cx cy 1 [obj mat subid p3d puv dist]; 0; ); ); let if (nBtn == 1) then strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " X down" else " A down" else strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " X up" else " A up" -> ename in SendPluginEvent obstr.POXR_inst ename nil nil; ); let nth_list ctrlstr.POBJOXRCTL_lTouchState ibtn -> pTouch in let nth_list ltouches ibtn -> nTouch in if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " X touch" else " A touch" else strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " X untouch" else " A untouch" -> ename in SendPluginEvent obstr.POXR_inst ename nil evtid; ); ); let if (i == 0) then BtnY else BtnB -> ibtn in ( let nth_list ctrlstr.POBJOXRCTL_lBtnState ibtn -> pBtn in let nth_list lbuttons ibtn -> nBtn in if (pBtn == nBtn) then nil else ( let if (nBtn == 1) then strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " Y down" else " B down" else strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " Y up" else " B up" -> ename in SendPluginEvent obstr.POXR_inst ename nil nil; ); let nth_list ctrlstr.POBJOXRCTL_lTouchState ibtn -> pTouch in let nth_list ltouches ibtn -> nTouch in if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " Y touch" else " B touch" else strcat ctrlstr.POBJOXRCTL_sName if (i == 0) then " Y untouch" else " B untouch" -> ename in SendPluginEvent obstr.POXR_inst ename nil evtid; ); ); let nth_list ctrlstr.POBJOXRCTL_lBtnState BtnTrigger -> pBtn in let nth_list lbuttons BtnTrigger -> nBtn in if (pBtn == nBtn) then nil else ( //control virtual pointer on widgets //if (obstr.POXR_bCurrentMouseRay != i) then nil else if (!ctrlstr.POBJOXRCTL_bState) then nil else ( let cursorpos -> [cx cy] in let SO3VirtualPointerGetRayInfos ctrlstr.POBJOXRCTL_oPointer -> [session obj mat subid p3d puv dist] in if (nBtn == 1) then ( SO3VirtualPointerSendClick ctrlstr.POBJOXRCTL_oPointer 1; if (((obstr.POXR_iTeleportMode == 2) && ctrlstr.POBJOXRCTL_iTeleportState) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i))) then nil else cbV3DviewPointerClick viewstr pid [(SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointer) (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointer)] cx cy 1 [obj mat subid p3d puv dist]; if ((obstr.POXR_iTeleportMode != 2) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i)) || ((obstr.POXR_iTeleportCur != nil) && (obstr.POXR_iTeleportCur != i))) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = ctrlstr.POBJOXRCTL_iTeleportState + 2; set obstr.POXR_iTeleportCur = i; ); 0; ) else ( SO3VirtualPointerSendUnClick ctrlstr.POBJOXRCTL_oPointer 1; if (((obstr.POXR_iTeleportMode == 2) && ctrlstr.POBJOXRCTL_iTeleportState) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i))) then nil else cbV3DviewPointerUnClick viewstr pid cx cy 1 [obj mat subid p3d puv dist]; 0; ); ); if ((nBtn == 0) || (!ctrlstr.POBJOXRCTL_bRayState) || (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj)) then nil else ( /*let 0 -> nc in let sizelist obstr.POXR_controllers -> nsize in while (nc < nsize) do ( let nth_list obstr.POXR_controllers nc -> sctrlstr2 in SO3VirtualPointerSetEnable sctrlstr2.POBJOXRCTL_oPointer 0; set nc = nc + 1; );*/ set obstr.POXR_bCurrentMouseRay = i; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 1; ); let if (nBtn == 1) then ( //addLogMessage strcat ctrlstr.POBJOXRCTL_sName " trigger down"; strcat ctrlstr.POBJOXRCTL_sName " trigger down" ) else ( //addLogMessage strcat ctrlstr.POBJOXRCTL_sName " trigger up"; strcat ctrlstr.POBJOXRCTL_sName " trigger up" ) -> ename in SendPluginEvent obstr.POXR_inst ename nil nil; ); let nth_list ctrlstr.POBJOXRCTL_lTouchState BtnTrigger -> pTouch in let nth_list ltouches BtnTrigger -> nTouch in if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName " trigger touch" else strcat ctrlstr.POBJOXRCTL_sName " trigger untouch" -> ename in SendPluginEvent obstr.POXR_inst ename nil evtid; ); let nth_list ctrlstr.POBJOXRCTL_lTouchState TouchPointing -> pTouch in let nth_list ltouches TouchPointing -> nTouch in if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName " index pointing" else strcat ctrlstr.POBJOXRCTL_sName " index not pointing" -> ename in SendPluginEvent obstr.POXR_inst ename nil evtid; ); let nth_list ctrlstr.POBJOXRCTL_lTouchState TouchThumbUp -> pTouch in let nth_list ltouches TouchThumbUp -> nTouch in if (pTouch == nTouch) then nil else ( let if (nTouch == 1) then strcat ctrlstr.POBJOXRCTL_sName " thumb untouch" else strcat ctrlstr.POBJOXRCTL_sName " thumb touch" -> ename in SendPluginEvent obstr.POXR_inst ename nil evtid; ); set ctrlstr.POBJOXRCTL_lBtnState = lbuttons; set ctrlstr.POBJOXRCTL_lTouchState = ltouches; set ctrlstr.POBJOXRCTL_lAxis = [padx pady triggerz gripw]; ); if (ctrlstr.POBJOXRCTL_objTrigger == nil) then nil else SO3ObjectSetOrientation ctrlstr.POBJOXRCTL_objTrigger SO3MathsEulerPYRToQuat [(-.triggerz) *. 0.15 0.0 0.0]; if (ctrlstr.POBJOXRCTL_objTrackPip == nil) then nil else SO3ObjectSetPosition ctrlstr.POBJOXRCTL_objTrackPip [(padx *. 0.019) (pady *. 0.0019) (pady *. (-.0.019))]; ); //teleport if (!ctrlstr.POBJOXRCTL_bState || (obstr.POXR_iTeleportMode == 0) || ((obstr.POXR_iTeleportController > 0) && ((obstr.POXR_iTeleportController - 1) != i))) then nil else ( //force ray on pad controller if (!ctrlstr.POBJOXRCTL_iTeleportState || (!ctrlstr.POBJOXRCTL_bRayState) || /*(obstr.POXR_bCurrentMouseRay == i) ||*/ (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj)) then nil else ( /*let 0 -> nc in let sizelist obstr.POXR_controllers -> nsize in while (nc < nsize) do ( let nth_list obstr.POXR_controllers nc -> sctrlstr2 in SO3VirtualPointerSetEnable sctrlstr2.POBJOXRCTL_oPointer 0; set nc = nc + 1; ); */ set obstr.POXR_bCurrentMouseRay = i; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 1; ); if ((np3d == nil) || (ctrlstr.POBJOXRCTL_iTeleportState == 2) || !ctrlstr.POBJOXRCTL_iTeleportState) then ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 0 0; 0; ) else if ((nobflag & iNodeFlagController) || (nobflag & iNodeFlagVUI) || (nobflag & iNodeFlagTools)) then nil else ( if (V3DphysGetState c3dXsession) then ( if (ctrlstr.POBJOXRCTL_pGrabbedBody != nil) then nil else let (getVectorDistanceF (SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointerSrc) np3d) +. 1.0 -> length in let normalizeVectorF (SO3MathsQuatGetDirection (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointerSrc) [0.0 0.0 (-.1.0)]) -> dest in let getValidRay (SO3PhysicsRayCastExt (V3DgetSession c3dXsession) (SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointerSrc) dest length) obstr ctrlstr i @isAnInvalidTeleportBody -> [tbody dist [nx ny nz]] in let addVectorF (SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointerSrc) (multiplyVectorF dest [dist dist dist]) -> [np3dx np3dy np3dz] in let (tbody == nil) || (ny <. 0.82) -> noray in ( SO3ObjectSetGlobalPosition ctrlstr.POBJOXRCTL_oTarget [np3dx np3dy np3dz]; SO3ObjectSetGlobalOrientation ctrlstr.POBJOXRCTL_oTarget (SO3MathsGetRotationToAxis [1.0 0.0 0.0] [nx ny nz]); SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget !noray 0; if (noray || (ctrlstr.POBJOXRCTL_iTeleportState != 3)) then nil else // not a plannar face ( SendPluginEvent obstr.POXR_inst "Teleport" strcatnSep (ftoa np3dx)::(ftoa np3dy)::(ftoa np3dz)::nil " " nil; set ctrlstr.POBJOXRCTL_iTeleportState = 0; set obstr.POXR_iTeleportCur = nil; ); ); 0; ) else ( SO3ObjectSetGlobalPosition ctrlstr.POBJOXRCTL_oTarget np3d; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 1 0; SO3ObjectSetGlobalOrientation ctrlstr.POBJOXRCTL_oTarget SO3MathsQuatAdd SO3ObjectGetGlobalOrientation camera [0.5 0.0 0.0 0.5]; if (ctrlstr.POBJOXRCTL_iTeleportState != 3) then nil else let np3d -> [np3dx np3dy np3dz] in ( SendPluginEvent obstr.POXR_inst "Teleport" strcatnSep (ftoa np3dx)::(ftoa np3dy)::(ftoa np3dz)::nil " " nil; set ctrlstr.POBJOXRCTL_iTeleportState = 0; set obstr.POXR_iTeleportCur = nil; ); 0; ); ); if (ctrlstr.POBJOXRCTL_iTeleportState != 3) then nil else ( set ctrlstr.POBJOXRCTL_iTeleportState = 0; set obstr.POXR_iTeleportCur = nil; ); ); //physic ray cast if (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj) then nil else ( if (ctrlstr.POBJOXRCTL_bState && ctrlstr.POBJOXRCTL_bGrab && (ctrlstr.POBJOXRCTL_pGrabbedBody == nil)) then let normalizeVectorF (SO3MathsQuatGetDirection SO3MathsQuatAdd ctloquat SO3MathsEulerPYRToQuat [SO3MathsDegreeToRadian 0.0 (if (i == 0) then (-.10.0) else 10.0) 0.0] [0.0 0.0 1.0]) -> dest in let addVectorF ctlpos (multiplyVectorF dest [0.01 0.01 0.01]) -> src in let getValidRay (SO3PhysicsRayCastExt (V3DgetSession c3dXsession) src dest 0.20) obstr ctrlstr i @isAnInvalidBody -> [rbody cdist rnormal] in let if rbody != nil then [rbody cdist rnormal] else //try again from hand ( set dest = normalizeVectorF (SO3MathsQuatGetDirection (SO3ObjectGetGlobalOrientation ctrlstr.POBJOXRCTL_oPointerSrc) [0.0 0.0 (-.1.0)]); set src = addVectorF (SO3ObjectGetGlobalPosition ctrlstr.POBJOXRCTL_oPointerSrc) (multiplyVectorF dest [0.01 0.01 0.01]); getValidRay (SO3PhysicsRayCastExt (V3DgetSession c3dXsession) src dest 0.10) obstr ctrlstr i @isAnInvalidBody; ) -> [rbody cdist rnormal] in ( if (rbody == nil) then nil else ( //check if the grabbed object can have a mass after it has been grabbed / otherwise ignore it let SO3BodyGetMassMatrix rbody -> [mass _] in if (mass <=. 0.0) then nil else ( if (ctrlstr.POBJOXRCTL_body != nil) then nil else ( set ctrlstr.POBJOXRCTL_pGrabBody = SO3BodyCreateEllipsoid ctrlstr.POBJOXRCTL_obj [0.05 0.05 0.05]; SO3BodySetType ctrlstr.POBJOXRCTL_pGrabBody 1; V3DphysSetBodyMaterial c3dXsession ctrlstr.POBJOXRCTL_pGrabBody "avatar"; let SO3BodyGetMassMatrix rbody -> [mass _] in SO3BodySetMass ctrlstr.POBJOXRCTL_pGrabBody minf 2.0 (mass *. 10.0); SO3BodySetAutoSleep ctrlstr.POBJOXRCTL_pGrabBody 0; SO3BodySetGravityEnable ctrlstr.POBJOXRCTL_pGrabBody 0; SO3BodySetIgnoreCollision ctrlstr.POBJOXRCTL_pGrabBody 1; ); set ctrlstr.POBJOXRCTL_pGrabJoint = SO3PhysicsContraintCreateSlider (V3DgetSession c3dXsession) (SO3SceneNodeGetBody ctrlstr.POBJOXRCTL_obj) rbody ctlpos [0.0 1.0 0.0] 1 0; SO3PhysicsContraintSetSliderLimits ctrlstr.POBJOXRCTL_pGrabJoint 0.0 0.0; SO3PhysicsContraintSetCollisionState ctrlstr.POBJOXRCTL_pGrabJoint 0; // if the body father have a body we limits the joint stiffness let SO3SceneNodeGetBody (SO3ObjectGetParent SO3BodyGetSceneNode rbody) -> pbody in let SO3BodyGetMassMatrix pbody -> [pmass _] in let if ((pbody != nil) && (pmass >. 0.0)) then 0.8 else 1.0 -> stiff in SO3PhysicsContraintSetStiffness ctrlstr.POBJOXRCTL_pGrabJoint stiff; SO3BodySetType rbody (SO3BodyGetType rbody) | 1 | 2; //set ctrlstr.POBJOXRCTL_bGrab = 0; set ctrlstr.POBJOXRCTL_pGrabbedBody = rbody; ); // grab the object let SO3ObjectGetName (SO3BodyGetSceneNode rbody) -> grabbedname in ( cbPlugGeneric 21 grabbedname nil; let strcat ctrlstr.POBJOXRCTL_sName " grab" -> ename in SendPluginEvent obstr.POXR_inst ename grabbedname evtid; ); ); 0; ) else if ((!ctrlstr.POBJOXRCTL_bState || !ctrlstr.POBJOXRCTL_bGrab) && (ctrlstr.POBJOXRCTL_pGrabbedBody != nil)) then ( SO3PhysicsContraintDestroy ctrlstr.POBJOXRCTL_pGrabJoint; SO3BodyDestroy ctrlstr.POBJOXRCTL_pGrabBody; set ctrlstr.POBJOXRCTL_pGrabJoint = nil; set ctrlstr.POBJOXRCTL_pGrabBody = nil; set ctrlstr.POBJOXRCTL_bGrab = 0; SO3BodySetVelocity ctrlstr.POBJOXRCTL_pGrabbedBody ctrlstr.POBJOXRCTL_fLastVel; SO3BodySetOmega ctrlstr.POBJOXRCTL_pGrabbedBody ctrlstr.POBJOXRCTL_fLastOmega; // ungrab the object let 0 -> nc in let sizelist obstr.POXR_controllers -> nsize in while (nc < nsize) do ( let nth_list obstr.POXR_controllers nc -> sctrlstr2 in if (sctrlstr2.POBJOXRCTL_pGrabbedBody == ctrlstr.POBJOXRCTL_pGrabbedBody) then nil else ( let SO3ObjectGetName (SO3BodyGetSceneNode ctrlstr.POBJOXRCTL_pGrabbedBody) -> grabbedname in ( SO3BodySetType ctrlstr.POBJOXRCTL_pGrabbedBody ((SO3BodyGetType ctrlstr.POBJOXRCTL_pGrabbedBody) & ~(1)) & ~(2); cbPlugGeneric 22 grabbedname nil; let strcat ctrlstr.POBJOXRCTL_sName " ungrab" -> ename in SendPluginEvent obstr.POXR_inst ename grabbedname evtid; ); ); set nc = nc + 1; ); set ctrlstr.POBJOXRCTL_pGrabbedBody = nil; 0; ) else nil; ); //allow to grab only once if (ctrlstr.POBJOXRCTL_bGrab && (ctrlstr.POBJOXRCTL_pGrabbedBody != nil)) then set ctrlstr.POBJOXRCTL_bGrab = 1 else set ctrlstr.POBJOXRCTL_bGrab = max 0 (ctrlstr.POBJOXRCTL_bGrab - 1); //rumble if (ctrlstr.POBJOXRCTL_iRumbleDuration <= 0) then nil else ( let _tickcount -> crtime in let crtime - ctrlstr.POBJOXRCTL_iRumbleTime -> sptime in let if sptime == 0 then 1 else sptime -> sptime in ( set ctrlstr.POBJOXRCTL_iRumbleDuration = ctrlstr.POBJOXRCTL_iRumbleDuration - sptime; set ctrlstr.POBJOXRCTL_iRumbleTime = crtime; ); _SetOpenXrControllerRumble obstr.POXR_device i ctrlstr.POBJOXRCTL_fRumbleVal; ); ); ); ); if (doagain == 1) then ( set doagain = doagain + 1; set i = 0; ) else set i = i + 1; ); ); ); ); 0; ); 0;; fun cbOpenXrPostRender(inst, viewstr, obstr)= if (obstr.POXR_bLastUpdateMode != 2) then nil else ( set obstr.POXR_bLastUpdateMode = 0; V3DcameraTeleport (V3DgetSessionView c3dXsession) (V3DgetDefaultCamera c3dXsession); ); let SO3BufferGetStereoTextures viewstr.V3D_buffer -> [lptr rptr type] in _UpdateOpenXrTextures obstr.POXR_device lptr rptr; 0;; fun startStereo(obstr)= let V3DgetSessionView c3dXsession -> viewstr in let _GetOpenXrTextureSize obstr.POXR_device -> texsize in let c3dXsession -> sessionstr in ( let texsize -> [vw vh] in set tVRTEXTUREVIEW = [0 0 vw vh]; SO3BufferSetStereoMeshTextureSize viewstr.V3D_buffer texsize texsize; SO3BufferSetStereoMode viewstr.V3D_buffer SO3_SM_OPENXR; set obstr.POXR_lostTick = 0; set obstr.POXR_iFrameAcc = 0; set obstr.POXR_iNbFrame = 0; V3DsetVrMode viewstr 1; //force viewport size update V3DsetViewSizeDirty viewstr; ); 0;; fun stopStereo(obstr)= let V3DgetSessionView c3dXsession -> viewstr in ( SO3BufferSetStereoMode viewstr.V3D_buffer SO3_SM_NONE; SO3BufferSetStereoProjectionMatrix viewstr.V3D_buffer nil nil 0; SO3BufferSetStereoMeshTextureSize viewstr.V3D_buffer [1 1] [1 1]; SO3BufferSetStereoAspectRatio viewstr.V3D_buffer 0.0; SO3BufferSetStereoFOVy viewstr.V3D_buffer 0.0; V3DsetVrMode viewstr 0; //force viewport size update V3DsetViewSizeDirty viewstr; ); 0;; fun cbChangeCamera(inst, viewstr, sessionstr, camera, obstr)= let SO3CameraGetNearClipDistance camera -> nearclip in let SO3CameraGetFarClipDistance camera -> farclip in let _GetOpenXrProjectionMatrix obstr.POXR_device nearclip farclip -> pmat in if (pmat == nil) then nil else let pmat -> [lmat rmat] in SO3BufferSetStereoProjectionMatrix sessionstr.V3D_sessionView.V3D_buffer lmat rmat 1; set obstr.POXR_tLastPos = nil; set obstr.POXR_tLastYPR = nil; 0;; fun cbReset(inst, from, action, param, reply, obstr)= set obstr.POXR_tLastPos = nil; set obstr.POXR_tLastYPR = nil; 0;; fun disableHmd(obstr)= setPluginInstanceCbPreRender obstr.POXR_inst nil; setPluginInstanceCbPostRender obstr.POXR_inst nil; setPluginInstanceCbCameraChange obstr.POXR_inst nil; stopStereo obstr; if (obstr.POXR_device == nil) then nil else ( set obstr.POXR_bConnected = 0; set obstr.POXR_tLastYPR = nil; stopStereo obstr; let sizelist obstr.POXR_controllers -> size in let 0 -> i in while (i < size) do ( let nth_list obstr.POXR_controllers i -> ctrlstr in SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 0; set i = i + 1; ); ); _DSopenXrDevice obstr.POXR_device; set obstr.POXR_device = nil; set obstr.POXR_iTeleportCur = nil; 0;; fun cbEnablePassthrough(inst, from, action, param, reply, obstr)= let V3DgetDefaultViewport (V3DgetSessionView c3dXsession) -> viewportstr in let get_rgba (V3DgetViewportColor viewportstr) -> [r g b _] in V3DsetViewportColor viewportstr (make_rgba r g b 0); _SetOpenXrPassthroughEnable obstr.POXR_device 1; 0;; fun cbDisablePassthrough(inst, from, action, param, reply, obstr)= _SetOpenXrPassthroughEnable obstr.POXR_device 0; let V3DgetDefaultViewport (V3DgetSessionView c3dXsession) -> viewportstr in let get_rgba (V3DgetViewportColor viewportstr) -> [r g b _] in V3DsetViewportColor viewportstr (make_rgba r g b 255); 0;; fun cbEnable(inst, from, action, param, reply, obstr)= let if obstr.POXR_bHandTracking then OPENXR_HAND_TRACKING_EXTENSION else 0 -> handtracking in let if obstr.POXR_bPassthrough then OPENXR_PASSTHROUGH_EXTENSION else 0 -> passthrough in _SetOpenXrExtensions handtracking|passthrough; _SetOpenXrAppName inst.INST_groupstr.GRP_project.PRJ_sName; if (obstr.POXR_device != nil) then nil else set obstr.POXR_device = _CRopenXrDevice _channel SO3GetActiveRenderer obstr.POXR_fScaleRatio; if (obstr.POXR_device == nil) then ( SendPluginEvent obstr.POXR_inst "Device not found" nil nil; ) else ( set obstr.POXR_bConnected = 1; startStereo obstr; setPluginInstanceCbScenePreRender obstr.POXR_inst mkfun4 @cbOpenXrPreRenderCam obstr; setPluginInstanceCbPreRender obstr.POXR_inst mkfun3 @cbOpenXrPreRender obstr; setPluginInstanceCbPostRender obstr.POXR_inst mkfun3 @cbOpenXrPostRender obstr; setPluginInstanceCbCameraChange obstr.POXR_inst mkfun5 @cbChangeCamera obstr; let sizelist obstr.POXR_controllers -> size in let 0 -> haspointer in ( let 0 -> i in while (i < size) do ( let nth_list obstr.POXR_controllers i -> ctrlstr in if ((ctrlstr.POBJOXRCTL_oPointer == nil) || (!ctrlstr.POBJOXRCTL_bRayState)) then nil else ( SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 1; set haspointer = 1; ); set i = i + 1; ); if (!haspointer) then nil else let V3DgetSessionView c3dXsession -> viewstr in V3DsetVrPointerState viewstr 1; ); SendPluginEvent obstr.POXR_inst "Device found" nil nil; ); 0;; fun cbDisable(inst, from, action, param, reply, obstr)= disableHmd obstr; let V3DgetSessionView c3dXsession -> viewstr in V3DsetVrPointerState viewstr 0; 0;; fun cbLoaded(inst, obstr)= cbEnable inst nil nil nil nil obstr; 0;; fun cbRumble(inst, from, action, param, reply, obstr, ctrlstr)= let atoi param -> val in let if (val == nil) then 250 else val -> val in ( set ctrlstr.POBJOXRCTL_fRumbleVal = 1.0; set ctrlstr.POBJOXRCTL_iRumbleDuration = val; set ctrlstr.POBJOXRCTL_iRumbleTime = _tickcount; ); 0;; fun cbGrab(inst, from, action, param, reply, obstr, ctrlstr)= set ctrlstr.POBJOXRCTL_bGrab = 5; 0;; fun cbUnGrab(inst, from, action, param, reply, obstr, ctrlstr)= set ctrlstr.POBJOXRCTL_bGrab = 0; 0;; fun cbSetControllerObject(inst, from, action, param, reply, obstr, ctrlstr)= let lineextr param -> lp in let V3DgetObjectByName c3dXsession hd lp -> father in let hd (strextr hd tl lp) -> lpos in let if (lpos == nil) then [0.0 0.0 0.0] else [(atof hd lpos) (atof hd tl lpos) (atof hd tl tl lpos)] -> offsetpos in let hd (strextr hd tl tl lp) -> lang in let if (lang == nil) then [0.0 0.0 0.0 1.0] else SO3MathsEulerYXZToQuat [SO3MathsDegreeToRadian (atof hd lang) SO3MathsDegreeToRadian (atof hd tl lang) SO3MathsDegreeToRadian (atof hd tl tl lang)] -> offsetquat in ( SO3PhysicsContraintDestroy ctrlstr.POBJOXRCTL_pGrabJoint; SO3BodyDestroy ctrlstr.POBJOXRCTL_pGrabBody; set ctrlstr.POBJOXRCTL_pGrabJoint = nil; set ctrlstr.POBJOXRCTL_pGrabBody = nil; if (ctrlstr.POBJOXRCTL_pGrabbedBody == nil) then nil else let SO3ObjectGetName (SO3BodyGetSceneNode ctrlstr.POBJOXRCTL_pGrabbedBody) -> grabbedname in let strcatn obstr.POXR_inst.INST_sName::"ctrl_"::ctrlstr.POBJOXRCTL_sName::nil -> evtid in ( cbPlugGeneric 22 grabbedname nil; let strcat ctrlstr.POBJOXRCTL_sName " ungrab" -> ename in SendPluginEvent obstr.POXR_inst ename grabbedname evtid; set ctrlstr.POBJOXRCTL_pGrabbedBody = nil; ); // reset default controller obj if (father == nil) then ( if (ctrlstr.POBJOXRCTL_obj == ctrlstr.POBJOXRCTL_defObj) then nil else ( SO3BodySetVelocity ctrlstr.POBJOXRCTL_body ctrlstr.POBJOXRCTL_fLastVel; SO3BodySetOmega ctrlstr.POBJOXRCTL_body ctrlstr.POBJOXRCTL_fLastOmega; SO3BodySetGravityEnable ctrlstr.POBJOXRCTL_body 1; SO3BodySetType ctrlstr.POBJOXRCTL_body ((SO3BodyGetType ctrlstr.POBJOXRCTL_body) & ~(1)) & ~(2); let SO3ObjectGetName (SO3BodyGetSceneNode ctrlstr.POBJOXRCTL_body) -> bodyname in cbPlugGeneric 22 bodyname nil; set father = ctrlstr.POBJOXRCTL_defObj; set ctrlstr.POBJOXRCTL_vOffset = ctrlstr.POBJOXRCTL_vDefOffset; let SO3SceneNodeGetBody father -> body in ( set ctrlstr.POBJOXRCTL_obj = father; set ctrlstr.POBJOXRCTL_body = body; set ctrlstr.POBJOXRCTL_objTrigger = getControllerTrigger ctrlstr.POBJOXRCTL_obj; set ctrlstr.POBJOXRCTL_objTrackPip = getControllerTrack ctrlstr.POBJOXRCTL_obj; setObjectVisibility ctrlstr.POBJOXRCTL_obj::nil ctrlstr.POBJOXRCTL_bState 1; SO3BodySetIgnoreCollision ctrlstr.POBJOXRCTL_body 0; ); ); //Show or hide the laser /*if (obstr.POXR_bCurrentMouseRay == ctrlstr.POBJOXRCTL_id) then (*/ if (!ctrlstr.POBJOXRCTL_bRayState) then nil else ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy (obstr.POXR_iShowRay == 1) 1; SO3VirtualPointerSetRayCastMode ctrlstr.POBJOXRCTL_oPointer if (obstr.POXR_iShowRay == 1) then 2 else 1; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 1; ); /*) else ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy 0 1; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 0; );*/ SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 0 0; ) else ( if (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj) then ( SO3BodySetVelocity ctrlstr.POBJOXRCTL_body ctrlstr.POBJOXRCTL_fLastVel; SO3BodySetOmega ctrlstr.POBJOXRCTL_body ctrlstr.POBJOXRCTL_fLastOmega; SO3BodySetGravityEnable ctrlstr.POBJOXRCTL_body 1; SO3BodySetType ctrlstr.POBJOXRCTL_body ((SO3BodyGetType ctrlstr.POBJOXRCTL_body) & ~(1)) & ~(2); let SO3ObjectGetName (SO3BodyGetSceneNode ctrlstr.POBJOXRCTL_body) -> bodyname in cbPlugGeneric 22 bodyname nil; ) else ( setObjectVisibility ctrlstr.POBJOXRCTL_obj::nil 0 1; SO3BodySetIgnoreCollision ctrlstr.POBJOXRCTL_body 1; ); let SO3SceneNodeGetBody father -> body in let V3DgetAvatarMaterial c3dXsession -> mat2 in ( set ctrlstr.POBJOXRCTL_vOffset = [offsetpos offsetquat]; set ctrlstr.POBJOXRCTL_obj = father; set ctrlstr.POBJOXRCTL_body = body; set ctrlstr.POBJOXRCTL_objTrigger = getControllerTrigger ctrlstr.POBJOXRCTL_obj; set ctrlstr.POBJOXRCTL_objTrackPip = getControllerTrack ctrlstr.POBJOXRCTL_obj; if (body == nil) then nil else ( let SO3BodyGetMaterial body -> mat1 in let if (mat1 == (V3DgetDefaultMaterial c3dXsession)) then mat2 else mat1 -> mat1 in SO3PhysicsMaterialSetDefaultCollidable mat1 mat2 0; SO3BodySetGravityEnable body 0; SO3BodySetType body (SO3BodyGetType body) | 1 | 2; ); ); set obstr.POXR_bCurrentMouseRay = !ctrlstr.POBJOXRCTL_id; let 0 -> i in while (i < 2) do ( let nth_list obstr.POXR_controllers i -> nctrlstr in ( //Show or hide the laser //if (obstr.POXR_bCurrentMouseRay == i) then if (!nctrlstr.POBJOXRCTL_bRayState) then nil else SO3VirtualPointerSetEnable nctrlstr.POBJOXRCTL_oPointer 1 /*else SO3VirtualPointerSetEnable nctrlstr.POBJOXRCTL_oPointer 0;*/ ); set i = i + 1; ); ); set ctrlstr.POBJOXRCTL_bObjChanged = 1; ); 0;; fun cbSetControllerOffset(inst, from, action, param, reply, obstr, ctrlstr)= let ctrlstr.POBJOXRCTL_vOffset -> [op oq] in let lineextr param -> lp in let hd (strextr hd lp) -> lpos in let if (lpos == nil) then op else [(atof hd lpos) (atof hd tl lpos) (atof hd tl tl lpos)] -> offsetpos in let hd (strextr hd tl lp) -> lang in let if (lang == nil) then oq else SO3MathsEulerYXZToQuat [SO3MathsDegreeToRadian (atof hd lang) SO3MathsDegreeToRadian (atof hd tl lang) SO3MathsDegreeToRadian (atof hd tl tl lang)] -> offsetquat in ( set ctrlstr.POBJOXRCTL_vOffset = [offsetpos offsetquat]; set ctrlstr.POBJOXRCTL_vDefOffset = [offsetpos offsetquat]; //if (ctrlstr.POBJOXRCTL_oPointerSrc != ctrlstr.POBJOXRCTL_defObj) then nil else //( // SO3ObjectSetOrientation ctrlstr.POBJOXRCTL_oPointer offsetquat; // SO3ObjectSetOrientation ctrlstr.POBJOXRCTL_oRayDummy offsetquat; //); ); 0;; fun setSliceFlagOnNode(l, state, sons)= if l == nil then nil else let hd l -> obj in ( if (!sons) then nil else setSliceFlagOnNode (SO3ObjectGetChildren obj) state sons; let SO3EntityMaterialList obj -> lmat in while (lmat != nil) do ( SO3MaterialSetIgnoreSlicePlane hd lmat state; set lmat = tl lmat; ); setSliceFlagOnNode (tl l) state sons; ); 0;; fun cbSetControllerRayState(inst, from, action, param, reply, p)= let p -> [obstr ctrlstr state] in ( set ctrlstr.POBJOXRCTL_bRayState = state; if (state) then ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy (obstr.POXR_iShowRay == 1) 1; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 0 0; SO3VirtualPointerSetRayCastMode ctrlstr.POBJOXRCTL_oPointer if (obstr.POXR_iShowRay == 1) then 2 else 1; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 1; ) else ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy 0 1; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 0 0; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 0; ); ); 0;; fun countBonesSons(b)= let 0 -> i in ( while (b != nil) do ( set b = hd (SO3ObjectGetChildren b); set i = i + 1; ); i; );; var HandBaseIndex = 0;; fun getHandBoneList(lp, np, skipnext)= if (lp == nil) then np else ( let hd lp -> b in if (skipnext) then ( set np = (getHandBoneList (SO3ObjectGetChildren b) np 0); ) else ( set HandBaseIndex = HandBaseIndex + 1; //addLogMessage strcatn ">> "::(SO3ObjectGetName b)::" > "::(itoa HandBaseIndex)::nil; let SO3ObjectGetOrientation b -> q in set np = [b q HandBaseIndex]::(getHandBoneList (SO3ObjectGetChildren b) np 0); ); getHandBoneList tl lp np 0; );; fun getHandBonesOrdered(lp, np)= if (lp == nil) then np else let SO3ObjectGetChildren hd lp -> lb in ( let lb -> lpinky in while (lpinky != nil) do ( let hd lpinky -> b in if ((strfindi "pinky" (SO3ObjectGetName b) 0) == nil) then nil else let countBonesSons b -> cnt in if (cnt <= 4) then ( set HandBaseIndex = if(cnt == 4) then OPENXR_HAND_JOINT_LITTLE_METACARPAL else OPENXR_HAND_JOINT_LITTLE_PROXIMAL; let SO3ObjectGetOrientation b -> q in set np = [b q HandBaseIndex]::(getHandBoneList (SO3ObjectGetChildren b) np 0); ) else set np = (getHandBoneList (SO3ObjectGetChildren b) np 0); set lpinky = tl lpinky; ); let lb -> lring in while (lring != nil) do ( let hd lring -> b in if ((strfindi "ring" (SO3ObjectGetName b) 0) == nil) then nil else let countBonesSons b -> cnt in if (cnt <= 4) then ( set HandBaseIndex = if(cnt == 4) then OPENXR_HAND_JOINT_RING_METACARPAL else OPENXR_HAND_JOINT_RING_PROXIMAL; let SO3ObjectGetOrientation b -> q in set np = [b q HandBaseIndex]::(getHandBoneList (SO3ObjectGetChildren b) np 0); ) else set np = (getHandBoneList (SO3ObjectGetChildren b) np 0); set lring = tl lring; ); let lb -> lmiddle in while (lmiddle != nil) do ( let hd lmiddle -> b in if ((strfindi "middle" (SO3ObjectGetName b) 0) == nil) then nil else let countBonesSons b -> cnt in if (cnt <= 4) then ( set HandBaseIndex = if(cnt == 4) then OPENXR_HAND_JOINT_MIDDLE_METACARPAL else OPENXR_HAND_JOINT_MIDDLE_PROXIMAL; let SO3ObjectGetOrientation b -> q in set np = [b q HandBaseIndex]::(getHandBoneList (SO3ObjectGetChildren b) np 0); ) else set np = (getHandBoneList (SO3ObjectGetChildren b) np 0); set lmiddle = tl lmiddle; ); let lb -> lindex in while (lindex != nil) do ( let hd lindex -> b in if ((strfindi "index" (SO3ObjectGetName b) 0) == nil) then nil else let countBonesSons b -> cnt in if (cnt <= 4) then ( set HandBaseIndex = if(cnt == 4) then OPENXR_HAND_JOINT_INDEX_METACARPAL else OPENXR_HAND_JOINT_INDEX_PROXIMAL; let SO3ObjectGetOrientation b -> q in set np = [b q HandBaseIndex]::(getHandBoneList (SO3ObjectGetChildren b) np 0); ) else set np = (getHandBoneList (SO3ObjectGetChildren b) np 0); set lindex = tl lindex; ); let lb -> lthumb in while (lthumb != nil) do ( let hd lthumb -> b in if ((strfindi "thumb" (SO3ObjectGetName b) 0) == nil) then nil else let countBonesSons b -> cnt in if (cnt <= 4) then ( set OCULUS_HAND_MODEL = if (cnt == 4) then 1 else 0; set HandBaseIndex = OPENXR_HAND_JOINT_THUMB_METACARPAL; let SO3ObjectGetOrientation b -> q in set np = [b q HandBaseIndex]::(getHandBoneList (SO3ObjectGetChildren b) np OCULUS_HAND_MODEL); ) else set np = (getHandBoneList (SO3ObjectGetChildren b) np 0); set lthumb = tl lthumb; ); getHandBonesOrdered tl lp np; );; fun loadController(inst, obstr, ctrlname, objname, offset, offsetquat, raysrc, raystate)= let sizelist obstr.POXR_controllers -> id in let V3DgetObjectByName c3dXsession objname -> father in let if ((objname == nil) || (!strcmp objname "")) then strcatn "vrctl."::(itoa (sizelist obstr.POXR_controllers))::"."::nil else objname -> objname in let V3DgetObjectByName c3dXsession raysrc -> raysrcobj in let if (raysrcobj == nil) then father else raysrcobj -> raysrcobj in let SO3SceneNodeGetBody father -> body in let V3DgetObjectTypeByName objname -> iobjmode in let SO3ObjectGetPosition father -> clpos in let SO3ObjectGetOrientation father -> clquat in let if (father == nil) then nil else SO3VirtualPointerCreate (V3DgetSession c3dXsession) strcat objname "pointer" -> lvpointer in let if (father == nil) then nil else SO3MaterialCreate (V3DgetSession c3dXsession) (strcat objname "ray.material") obstr.POXR_sGroupName -> lmatray in let if (father == nil) then nil else SO3SceneNodeCreate (V3DgetSession c3dXsession) (strcat objname ".shell") -> lray in let if (father == nil) then nil else SO3PlaneCreate (V3DgetSession c3dXsession) obstr.POXR_sGroupName (strcat objname ".ray1") [0.005 1.0] nil nil -> lobray1 in let if (father == nil) then nil else SO3PlaneCreate (V3DgetSession c3dXsession) obstr.POXR_sGroupName (strcat objname ".ray2") [0.005 1.0] nil nil -> lobray2 in let if (father == nil) then nil else getHandBonesOrdered (SO3GetRootBonesFromMesh father) nil -> bones in let mkObjCtlOxrStr[id ctrlname father father body nil nil bones 0::0::0::0::0::0::0::0::0::nil 0::0::0::0::0::0::1::0::0::nil [0.0 0.0 0.0 0.0] iobjmode [clpos clquat] 0 raystate 0.0 0 0 nil nil nil 0 raysrcobj lvpointer lray lobray1 lobray2 nil lmatray 1 nil [0.0 0.0 0.0] [0.0 0.0 0.0] [offset offsetquat] [offset offsetquat] 1 0 nil nil] -> sctrlstr in let V3DgetAvatarMaterial c3dXsession -> mat2 in let strcatn (getPluginDirectory (getInstancePlugin inst))::"/res/"::"raybase.mesh"::nil -> meshpath in let strcatn (getPluginDirectory (getInstancePlugin inst))::"/res/"::"raybase.material"::nil -> matpath in ( /*while (bones != nil) do ( let (hd bones) -> [b q] in addLogMessage SO3ObjectGetName b; set bones = tl bones; );*/ if (sctrlstr.POBJOXRCTL_oPointer == nil) then nil else ( V3DaddResource c3dXsession matpath obstr.POXR_sGroupName SO3_RESOURCE_MATERIAL; V3DaddResource c3dXsession meshpath obstr.POXR_sGroupName SO3_RESOURCE_MESH; SO3VirtualPointerSetRayCastMode sctrlstr.POBJOXRCTL_oPointer if (obstr.POXR_iShowRay == 1) then 2 else 1; SO3VirtualPointerSetMaxLength sctrlstr.POBJOXRCTL_oPointer 10.0; SO3VirtualPointerSetEnable sctrlstr.POBJOXRCTL_oPointer raystate; ); set sctrlstr.POBJOXRCTL_objTrigger = getControllerTrigger sctrlstr.POBJOXRCTL_obj; set sctrlstr.POBJOXRCTL_objTrackPip = getControllerTrack sctrlstr.POBJOXRCTL_obj; setObjectControlerFlags sctrlstr.POBJOXRCTL_defObj::nil iNodeFlagController 1 1; if (body == nil) then nil else ( let SO3BodyGetMaterial body -> mat1 in let if (mat1 == (V3DgetDefaultMaterial c3dXsession)) then mat2 else mat1 -> mat1 in SO3PhysicsMaterialSetDefaultCollidable mat1 mat2 0; SO3BodySetGravityEnable body 0; SO3BodySetType body (SO3BodyGetType body) | 1 | 2; ); //Ignore slice on all controller materials setSliceFlagOnNode father::nil 1 1; //link virtual pointer to objects if (sctrlstr.POBJOXRCTL_oPointer == nil) then ( if (father == nil) then nil else addLogMessage "Virtual pointer creation failed on controller !"; 0; ) else ( set sctrlstr.POBJOXRCTL_oTarget = SO3SceneLoadEntity (V3DgetSession c3dXsession) obstr.POXR_sGroupName (strcat objname ".raybase") (_checkpack meshpath); SO3ObjectSetMouseClick sctrlstr.POBJOXRCTL_oPointerSrc 0; SO3ObjectSetMouseClick sctrlstr.POBJOXRCTL_obj 0; SO3ObjectSetVisible sctrlstr.POBJOXRCTL_oTarget 0 0; SO3ObjectSetRenderQueue sctrlstr.POBJOXRCTL_oTarget 65; SO3ObjectSetCastShadows sctrlstr.POBJOXRCTL_oTarget 0; SO3ObjectLink sctrlstr.POBJOXRCTL_oPointer sctrlstr.POBJOXRCTL_oPointerSrc; SO3ObjectSetPosition sctrlstr.POBJOXRCTL_oPointer if (sctrlstr.POBJOXRCTL_oPointerSrc != father) then [0.0 0.0 0.05] else SO3MathsQuatGetDirection offsetquat [0.0 0.0 0.05]; //if (sctrlstr.POBJOXRCTL_oPointerSrc != father) then nil else // SO3ObjectSetOrientation sctrlstr.POBJOXRCTL_oPointer offsetquat; SO3MaterialSetReceiveShadows lmatray 0; SO3MaterialSetAmbient lmatray make_rgba 255 0 0 96; SO3MaterialSetDiffuse lmatray make_rgba 255 0 0 96; SO3MaterialSetSelfIllumination lmatray make_rgba 255 0 0 96; SO3MaterialSetIgnoreSlicePlane lmatray 1; SO3MaterialSetPassCullingEnable lmatray 0 0 0; SO3MaterialSetPassDepthFunction lmatray 0 0 SO3_COMPARE_FUNCTION_ALWAYS_PASS; SO3EntitySetMaterial lobray1 lmatray 0; SO3EntitySetMaterial lobray2 lmatray 0; SO3ObjectSetCastShadows lobray1 0; SO3ObjectSetCastShadows lobray2 0; SO3ObjectSetMouseClick lobray1 0; SO3ObjectSetMouseClick lobray2 0; SO3ObjectLink lobray1 lray; SO3ObjectLink lobray2 lray; SO3ObjectLink lray sctrlstr.POBJOXRCTL_oPointerSrc; //if (sctrlstr.POBJOXRCTL_oPointerSrc != father) then nil else // SO3ObjectSetOrientation lray offsetquat; SO3ObjectSetOrientation lobray1 [1.0 0.0 0.0 0.0]; //90° on X SO3ObjectSetOrientation lobray2 SO3MathsQuatAdd [1.0 0.0 0.0 0.0] [0.0 0.0 0.5 0.5]; //90° on X and Z SO3ObjectSetPosition lobray1 [0.0 0.0 (-.0.5)]; SO3ObjectSetPosition lobray2 [0.0 0.0 (-.0.5)]; setObjectVisibility father::nil 0 1; setObjectRenderQueue sctrlstr.POBJOXRCTL_defObj::nil 66 1; 0; ); let strextr sctrlstr.POBJOXRCTL_sName -> ln in let strlowercase hd hd ln -> fw in let strcatnSep fw::(tl hd ln) " " -> cname in ( PluginRegisterAction inst strcat sctrlstr.POBJOXRCTL_sName " rumble" mkfun6 mkfun7 @cbRumble sctrlstr obstr; PluginRegisterAction inst strcatn "Set "::cname:: " object"::nil mkfun6 mkfun7 @cbSetControllerObject sctrlstr obstr; PluginRegisterAction inst strcatn "Set "::cname:: " offset"::nil mkfun6 mkfun7 @cbSetControllerOffset sctrlstr obstr; PluginRegisterAction inst strcat "Grab " cname mkfun6 mkfun7 @cbGrab sctrlstr obstr; PluginRegisterAction inst strcat "UnGrab " cname mkfun6 mkfun7 @cbUnGrab sctrlstr obstr; ); set obstr.POXR_controllers = lcat obstr.POXR_controllers sctrlstr::nil; sctrlstr; );; fun loadControllers(inst, obstr)= set obstr.POXR_controllers = nil; let getPluginInstanceParam inst "leftController" -> objlname in let atof (getPluginInstanceParam inst "loffposx") -> loffposx in let if loffposx == nil then 0.0 else loffposx -> loffposx in let atof (getPluginInstanceParam inst "loffposy") -> loffposy in let if loffposy == nil then 0.0 else loffposy -> loffposy in let atof (getPluginInstanceParam inst "loffposz") -> loffposz in let if loffposz == nil then 0.0 else loffposz -> loffposz in let atof (getPluginInstanceParam inst "loffangx") -> loffangx in let if loffangx == nil then 0.0 else loffangx -> loffangx in let atof (getPluginInstanceParam inst "loffangy") -> loffangy in let if loffangy == nil then 0.0 else loffangy -> loffangy in let atof (getPluginInstanceParam inst "loffangz") -> loffangz in let if loffangz == nil then 0.0 else loffangz -> loffangz in let getPluginInstanceParam inst "rightController" -> objrname in let atof (getPluginInstanceParam inst "roffposx") -> roffposx in let if roffposx == nil then 0.0 else roffposx -> roffposx in let atof (getPluginInstanceParam inst "roffposy") -> roffposy in let if roffposy == nil then 0.0 else roffposy -> roffposy in let atof (getPluginInstanceParam inst "roffposz") -> roffposz in let if roffposz == nil then 0.0 else roffposz -> roffposz in let atof (getPluginInstanceParam inst "roffangx") -> roffangx in let if roffangx == nil then 0.0 else roffangx -> roffangx in let atof (getPluginInstanceParam inst "roffangy") -> roffangy in let if roffangy == nil then 0.0 else roffangy -> roffangy in let atof (getPluginInstanceParam inst "roffangz") -> roffangz in let if roffangz == nil then 0.0 else roffangz -> roffangz in let atoi (getPluginInstanceParam inst "lraystate") -> lraystate in let if (lraystate == nil) then 1 else lraystate -> lraystate in let atoi (getPluginInstanceParam inst "rraystate") -> rraystate in let if (rraystate == nil) then 1 else rraystate -> rraystate in let getPluginInstanceParam inst "raysrcl" -> raysrcl in let getPluginInstanceParam inst "raysrcr" -> raysrcr in ( let SO3MathsEulerYXZToQuat [(SO3MathsDegreeToRadian loffangx) (SO3MathsDegreeToRadian loffangy) (SO3MathsDegreeToRadian loffangz)] -> lquat in let loadController inst obstr "Left controller" objlname [loffposx loffposy loffposz] lquat raysrcl lraystate -> ctrlstr in ( PluginRegisterAction inst "Left controller enable ray" mkfun6 @cbSetControllerRayState [obstr ctrlstr 1]; PluginRegisterAction inst "Left controller disable ray" mkfun6 @cbSetControllerRayState [obstr ctrlstr 0]; ); let SO3MathsEulerYXZToQuat [(SO3MathsDegreeToRadian roffangx) (SO3MathsDegreeToRadian roffangy) (SO3MathsDegreeToRadian roffangz)] -> rquat in let loadController inst obstr "Right controller" objrname [roffposx roffposy roffposz] rquat raysrcr rraystate -> ctrlstr in ( PluginRegisterAction inst "Right controller enable ray" mkfun6 @cbSetControllerRayState [obstr ctrlstr 1]; PluginRegisterAction inst "Right controller disable ray" mkfun6 @cbSetControllerRayState [obstr ctrlstr 0]; ); let nil -> l in let nil -> trackername in let 0 -> i in ( while ((set trackername = getPluginInstanceParam inst (strcat "trackerName_" (itoa i))) != nil) do ( let getPluginInstanceParam inst (strcat "trackerObj_" (itoa i)) -> trackerobj in let atoi (getPluginInstanceParam inst (strcat "trackerRayState_" (itoa i))) -> raystate in let atof (getPluginInstanceParam inst (strcat "trackerOffsetpx_" (itoa i))) -> offposx in let atof (getPluginInstanceParam inst (strcat "trackerOffsetpy_" (itoa i))) -> offposy in let atof (getPluginInstanceParam inst (strcat "trackerOffsetpz_" (itoa i))) -> offposz in let atof (getPluginInstanceParam inst (strcat "trackerOffsetax_" (itoa i))) -> offangx in let atof (getPluginInstanceParam inst (strcat "trackerOffsetay_" (itoa i))) -> offangy in let atof (getPluginInstanceParam inst (strcat "trackerOffsetaz_" (itoa i))) -> offangz in let SO3MathsEulerYXZToQuat [(SO3MathsDegreeToRadian offangx) (SO3MathsDegreeToRadian offangy) (SO3MathsDegreeToRadian offangz)] -> rquat in let loadController inst obstr trackername trackerobj [offposx offposy offposz] rquat nil raystate -> ctrlstr in ( PluginRegisterAction inst (strcat trackername " enable ray") mkfun6 @cbSetControllerRayState [obstr ctrlstr 1]; PluginRegisterAction inst (strcat trackername " disable ray") mkfun6 @cbSetControllerRayState [obstr ctrlstr 0]; ); set i = i + 1; ); ); ); 0;; fun deleteOb(inst, obstr)= setPluginInstanceCbPreRender inst nil; setPluginInstanceCbPostRender inst nil; _DSopenXrDevice obstr.POXR_device; stopStereo obstr; while (obstr.POXR_controllers != nil) do ( let hd obstr.POXR_controllers -> ctrlstr in let ctrlstr.POBJOXRCTL_initPos -> [pos quat] in ( SO3ObjectSetPosition ctrlstr.POBJOXRCTL_obj pos; SO3ObjectSetOrientation ctrlstr.POBJOXRCTL_obj quat; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_obj 1 1; SO3PhysicsContraintDestroy ctrlstr.POBJOXRCTL_pGrabJoint; SO3BodyDestroy ctrlstr.POBJOXRCTL_pGrabBody; SO3BodySetGravityEnable ctrlstr.POBJOXRCTL_body 1; SO3BodySetIgnoreCollision ctrlstr.POBJOXRCTL_body 0; SO3BodySetType ctrlstr.POBJOXRCTL_body ((SO3BodyGetType ctrlstr.POBJOXRCTL_body) & ~(1)) & ~(2); SO3ObjectDestroy ctrlstr.POBJOXRCTL_oPointer; SO3ObjectDestroy ctrlstr.POBJOXRCTL_oRay1; SO3ObjectDestroy ctrlstr.POBJOXRCTL_oRay2; SO3ObjectDestroy ctrlstr.POBJOXRCTL_oRayDummy; SO3ObjectDestroy ctrlstr.POBJOXRCTL_oTarget; SO3MaterialDestroy ctrlstr.POBJOXRCTL_matRay; SO3ObjectSetMouseClick ctrlstr.POBJOXRCTL_oPointerSrc 1; SO3ObjectSetMouseClick ctrlstr.POBJOXRCTL_obj 1; setObjectControlerFlags ctrlstr.POBJOXRCTL_defObj::nil iNodeFlagController 0 1; ); set obstr.POXR_controllers = tl obstr.POXR_controllers; ); SO3GroupDelete (V3DgetSession c3dXsession) obstr.POXR_sGroupName; let V3DgetSessionView c3dXsession -> viewstr in V3DsetVrPointerState viewstr 0; 0;; fun cbEnableControllers(inst, from, action, param, reply, obstr)= if (!obstr.POXR_bConnected) then nil else ( set obstr.POXR_bCtrlState = 1; let 0 -> i in let sizelist obstr.POXR_controllers -> size in while (i < size) do ( let nth_list obstr.POXR_controllers i -> ctrlstr in ( if (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj) then nil else setObjectVisibility ctrlstr.POBJOXRCTL_obj::nil ctrlstr.POBJOXRCTL_bState 1; //Show or hide the laser //if (obstr.POXR_bCurrentMouseRay == i) then ( if (!ctrlstr.POBJOXRCTL_bRayState) then nil else ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy (obstr.POXR_iShowRay == 1) 1; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oTarget 0 0; SO3VirtualPointerSetRayCastMode ctrlstr.POBJOXRCTL_oPointer if (obstr.POXR_iShowRay == 1) then 2 else 1; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 1; ); ) /*else ( SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy 0 1; SO3VirtualPointerSetEnable ctrlstr.POBJOXRCTL_oPointer 0; );*/ ); set i = i + 1; ); ); 0;; fun cbDisableControllers(inst, from, action, param, reply, obstr)= if (!obstr.POXR_bConnected) then nil else ( set obstr.POXR_bCtrlState = 0; set obstr.POXR_iTeleportCur = nil; let 0 -> i in let sizelist obstr.POXR_controllers -> size in while (i < size) do ( let nth_list obstr.POXR_controllers i -> ctrlstr in ( if (ctrlstr.POBJOXRCTL_obj != ctrlstr.POBJOXRCTL_defObj) then nil else setObjectVisibility ctrlstr.POBJOXRCTL_obj::nil 0 1; SO3ObjectSetVisible ctrlstr.POBJOXRCTL_oRayDummy 0 1; ); set i = i + 1; ); ); 0;; fun newOb(inst)= let atoi(getPluginInstanceParam inst "init") -> init in let atoi (getPluginInstanceParam inst "ignorecontrphys") -> ignorecontrphys in let if (ignorecontrphys == nil) then 1 else ignorecontrphys -> ignorecontrphys in let atoi (getPluginInstanceParam inst "showray") -> showray in let if (showray == nil) then 1 else showray -> showray in let atoi (getPluginInstanceParam inst "teleportmode") -> teleportmode in let if (teleportmode == nil) then 2 else teleportmode -> teleportmode in let atoi (getPluginInstanceParam inst "teleportcontroller") -> teleportcontroller in let if (teleportcontroller == nil) then 0 else teleportcontroller -> teleportcontroller in let atoi (getPluginInstanceParam inst "useinitialposition") -> useinitialposition in let if (useinitialposition == nil) then 0 else useinitialposition -> useinitialposition in let atoi (getPluginInstanceParam inst "autoclick") -> autoclick in let if (autoclick == nil) then 0 else autoclick -> autoclick in let atof (getPluginInstanceParam inst "autoclickdist") -> autoclickdist in let if (autoclickdist == nil) then 0.05 else autoclickdist -> autoclickdist in let atof (getPluginInstanceParam inst "scaleratio") -> scaleratio in let if (scaleratio == nil) then 1.0 else scaleratio -> scaleratio in let atoi (getPluginInstanceParam inst "handtracking") -> handtracking in let if (handtracking == nil) then 1 else handtracking -> handtracking in let atoi (getPluginInstanceParam inst "passthrough") -> passthrough in let if (passthrough == nil) then 0 else passthrough -> passthrough in let (IsInEditor inst) || IsEventLinked inst "Control" -> bcontrol in let (IsInEditor inst) || IsEventLinked inst "Orientation" -> borientation in let (IsInEditor inst) || IsEventLinked inst "Position" -> bposition in let (IsInEditor inst) || IsEventLinked inst "Left controller control" -> blccontrol in let (IsInEditor inst) || IsEventLinked inst "Left controller orientation" -> blcorientation in let (IsInEditor inst) || IsEventLinked inst "Left controller position" -> blcposition in let (IsInEditor inst) || IsEventLinked inst "Left controller trigger value" -> blctriggervalue in let (IsInEditor inst) || IsEventLinked inst "Left controller grip value" -> blcgripvalue in let (IsInEditor inst) || IsEventLinked inst "Left controller stick" -> blcstickvalue in let (IsInEditor inst) || IsEventLinked inst "Right controller control" -> brccontrol in let (IsInEditor inst) || IsEventLinked inst "Right controller orientation" -> brcorientation in let (IsInEditor inst) || IsEventLinked inst "Right controller position" -> brcposition in let (IsInEditor inst) || IsEventLinked inst "Right controller trigger value" -> brctriggervalue in let (IsInEditor inst) || IsEventLinked inst "Right controller grip value" -> brcgripvalue in let (IsInEditor inst) || IsEventLinked inst "Right controller stick" -> brcstickvalue in let mkObjOpenXrStr [inst (strcat (getPluginInstanceName inst) "_Group") nil handtracking passthrough nil nil nil nil 0 0 0 0 nil useinitialposition bcontrol borientation bposition blccontrol blcorientation blcposition blctriggervalue blcgripvalue blcstickvalue brccontrol brcorientation brcposition brctriggervalue brcgripvalue brcstickvalue ignorecontrphys 0 0 0 1 showray showray teleportmode teleportcontroller nil autoclick autoclickdist scaleratio] -> obstr in ( SO3GroupCreate (V3DgetSession c3dXsession) obstr.POXR_sGroupName; loadControllers inst obstr; if (!init) then nil else ( if inst.INST_groupstr.GRP_project.PRJ_bPluginsLoaded then ( cbEnable inst nil nil nil nil obstr; 0; ) else ( setPluginInstanceCbAllPluginsLoaded inst mkfun2 @cbLoaded obstr; 0; ); ); PluginRegisterAction inst "Enable passthrough" mkfun6 @cbEnablePassthrough obstr; PluginRegisterAction inst "Disable passthrough" mkfun6 @cbDisablePassthrough obstr; PluginRegisterAction inst "Reset" mkfun6 @cbReset obstr; PluginRegisterAction inst "Enable" mkfun6 @cbEnable obstr; PluginRegisterAction inst "Disable" mkfun6 @cbDisable obstr; PluginRegisterAction inst "Show ray" mkfun6 @cbShowRay obstr; PluginRegisterAction inst "Hide ray" mkfun6 @cbHideRay obstr; PluginRegisterAction inst "Set teleport mode" mkfun6 @cbSetTeleportMode obstr; PluginRegisterAction inst "Enable controllers" mkfun6 @cbEnableControllers obstr; PluginRegisterAction inst "Disable controllers" mkfun6 @cbDisableControllers obstr; setPluginInstanceCbDel inst mkfun2 @deleteOb obstr; ); 0;; fun IniPlug(file)= PlugRegister @newOb nil; setPluginEditor @dynamicedit; 0;;