using System; using UnityEngine; using System.Collections; using System.Collections.Generic; using SimpleJSON; namespace ky1001 { public class Searchlight : MVRScript { #region PluginInfo public string pluginAuthor = "ky1001"; public string pluginName = "Searchlight"; public string pluginVersion = "9.2"; public string pluginDate = "2023-07-09"; public string pluginDescription = ""; #endregion #region Var private UIDynamicToggle en_Toggle; private JSONStorableBool en_Bool; private UIDynamicToggle rev_Toggle; private JSONStorableBool rev_Bool; private UIDynamicToggle line_Toggle; private JSONStorableBool line_Bool; private JSONStorableBool vu_Bool; private UIDynamicToggle mv_Toggle; private JSONStorableBool mv_Bool; protected JSONStorableStringChooser vectorJSON; protected JSONStorableStringChooser atomJSON; protected JSONStorableStringChooser receiverJSON; protected UIDynamicPopup dp; private JSONStorableFloat X; private JSONStorableFloat Y; private JSONStorableFloat Z; private UIDynamicSlider sX; private UIDynamicSlider sY; private UIDynamicSlider sZ; private JSONStorableFloat Xc; private JSONStorableFloat Yc; private JSONStorableFloat Zc; private UIDynamicSlider sXc; private UIDynamicSlider sYc; private UIDynamicSlider sZc; private JSONStorableFloat tDZx; private JSONStorableFloat tDZy; private JSONStorableFloat tDZz; private UIDynamicSlider stDZx; private UIDynamicSlider stDZy; private UIDynamicSlider stDZz; private JSONStorableFloat mvFx; private UIDynamicSlider smvFx; private JSONStorableFloat mvFy; private UIDynamicSlider smvFy; private JSONStorableFloat mvFz; private UIDynamicSlider smvFz; Vector3 targetPastPosition; Vector3 targetPosition; Vector3 currentPastPosition; Vector3 v3; Vector3 targetAtomPosition; Vector3 currentAtomPosition; Vector3 aim; Quaternion look; Atom targetAtom; protected Atom receivingAtom; GameObject line = null; private float pastDZx; private float pastDZy; private float pastDZz; private JSONStorableBool _isKeepHorToCam; #endregion public override void Init() { try { // put init code in here en_Bool = new JSONStorableBool("Enable Trace Target", true); en_Toggle = CreateToggle(en_Bool, false); rev_Bool = new JSONStorableBool("Reverse", false); rev_Toggle = CreateToggle(rev_Bool, false); line_Bool = new JSONStorableBool("Draw Line", false); line_Toggle = CreateToggle(line_Bool, false); List vectorChoices = new List(); vectorChoices.Add("None"); vectorChoices.Add("up"); vectorChoices.Add("down"); vectorChoices.Add("left"); vectorChoices.Add("right"); vectorChoices.Add("forward"); vectorChoices.Add("back"); vectorJSON = new JSONStorableStringChooser("Vector3 direction", vectorChoices, "None", "Vector3 direction"); dp = CreateScrollablePopup(vectorJSON, false); dp.popupPanelHeight = 460f; vu_Bool = new JSONStorableBool("Vector3 up", true); //vu_Toggle = CreateToggle(vu_Bool, false); tDZx = new JSONStorableFloat("Target Dead Zone X adjustment", 0f, 0f, 10.0f, true); stDZx = CreateSlider(tDZx, false); tDZy = new JSONStorableFloat("Target Dead Zone Y adjustment", 0f, 0f, 10.0f, true); stDZy = CreateSlider(tDZy, false); tDZz = new JSONStorableFloat("Target Dead Zone Z adjustment", 0f, 0f, 10.0f, true); stDZz = CreateSlider(tDZz, false); var spacer = CreateSpacer(false); spacer.height = 20f; mv_Bool = new JSONStorableBool("Moving Factor", false); mv_Toggle = CreateToggle(mv_Bool, false); mvFx = new JSONStorableFloat("X Moving Factor", 1.0f, 0f, 1.0f, true); smvFx = CreateSlider(mvFx, false); mvFy = new JSONStorableFloat("Y Moving Factor", 1.0f, 0f, 1.0f, true); smvFy = CreateSlider(mvFy, false); mvFz = new JSONStorableFloat("Z Moving Factor", 1.0f, 0f, 1.0f, true); smvFz = CreateSlider(mvFz, false); mkList(); receiverJSON = new JSONStorableStringChooser("Target Receiver", null, "None", "Target Receiver"); dp = CreateScrollablePopup(receiverJSON, true); dp.popupPanelHeight = 960f; _isKeepHorToCam = new JSONStorableBool("Keep Horizontal to Camera", false); CreateToggle(_isKeepHorToCam, true); spacer = CreateSpacer(true); spacer.height = 0f; X = new JSONStorableFloat("Target X adjustment", 0f, -2.0f, 2.0f, true); sX = CreateSlider(X, true); Y = new JSONStorableFloat("Target Y adjustment", 0f, -2.0f, 2.0f, true); sY = CreateSlider(Y, true); Z = new JSONStorableFloat("Target Z adjustment", 0f, -2.0f, 2.0f, true); sZ = CreateSlider(Z, true); spacer = CreateSpacer(true); spacer.height = 85f; Xc = new JSONStorableFloat("Current X adjustment", 0f, -2.0f, 2.0f, true); sXc = CreateSlider(Xc, true); Yc = new JSONStorableFloat("Current Y adjustment", 0f, -2.0f, 2.0f, true); sYc = CreateSlider(Yc, true); Zc = new JSONStorableFloat("Current Z adjustment", 0f, -2.0f, 2.0f, true); sZc = CreateSlider(Zc, true); RegisterBool(en_Bool); RegisterBool(rev_Bool); RegisterBool(line_Bool); RegisterStringChooser(vectorJSON); RegisterBool(vu_Bool); RegisterFloat(tDZx); RegisterFloat(tDZy); RegisterFloat(tDZz); RegisterBool(mv_Bool); RegisterFloat(mvFx); RegisterFloat(mvFy); RegisterFloat(mvFz); RegisterStringChooser(receiverJSON); RegisterBool(_isKeepHorToCam); RegisterFloat(X); RegisterFloat(Y); RegisterFloat(Z); RegisterFloat(Xc); RegisterFloat(Yc); RegisterFloat(Zc); } catch (Exception e) { SuperController.LogError("Exception caught: " + e); } } // make atom selector public void mkList() { List targetChoices = new List(); foreach (string atomUID in SuperController.singleton.GetAtomUIDs()) { targetAtom = SuperController.singleton.GetAtomByUid(atomUID); if (targetAtom != containingAtom && targetAtom.hidden == false && targetAtom.GetBoolJSONParam("on").val == true && targetAtom.name != "CoreControl") { targetChoices.Add(atomUID); } } atomJSON = new JSONStorableStringChooser("Target Atom", targetChoices, "None", "Target Atom", SyncAtom); RegisterStringChooser(atomJSON); dp = CreateScrollablePopup(atomJSON, true); dp.popupPanelHeight = 1100f; } // receiver Atom protected void SyncAtom(string atomUID) { List receiverChoices = new List(); if (atomUID != null) { receivingAtom = SuperController.singleton.GetAtomByUid(atomUID); if (receivingAtom != null) { FreeControllerV3[] controls = receivingAtom.freeControllers; foreach (var receiverChoice in controls) { string temp_string = receiverChoice.ToString(); temp_string = temp_string.Substring(0, temp_string.Length - 19); if (receivingAtom.GetStorableByID(temp_string) != null) { receiverChoices.Add(temp_string); } } if (atomUID == "[CameraRig]") { receiverChoices.Add("CenterEye"); receiverChoices.Add("LeftHand"); receiverChoices.Add("RightHand"); } if (receivingAtom.type == "Person") { receiverChoices.Add("LipTrigger"); receiverChoices.Add("MouthTrigger"); receiverChoices.Add("ThroatTrigger"); receiverChoices.Add("LabiaTrigger"); receiverChoices.Add("VaginaTrigger"); receiverChoices.Add("DeepVaginaTrigger"); receiverChoices.Add("DeeperVaginaTrigger"); } } } else { receivingAtom = null; } receiverJSON.choices = receiverChoices; receiverJSON.val = "None"; } // Start is called once before Update or FixedUpdate is called and after Init() void Start() { try { List targetChoices = new List(); targetChoices = SuperController.singleton.GetAtomUIDs(); if (!targetChoices.Contains(atomJSON.val)) { atomJSON.val = "None"; receiverJSON.val = "None"; } } catch (Exception e) { SuperController.LogError("Exception caught: " + e); } } // Update is called with each rendered frame by Unity void Update() { try { // put code in here if (vectorJSON.val == "up") { v3 = Vector3.up; } if (vectorJSON.val == "down") { v3 = Vector3.down; } if (vectorJSON.val == "left") { v3 = Vector3.left; } if (vectorJSON.val == "right") { v3 = Vector3.right; } if (vectorJSON.val == "forward") { v3 = Vector3.forward; } if (vectorJSON.val == "back") { v3 = Vector3.back; } if (vectorJSON.val == "None" && vu_Bool.val == true) { v3 = Vector3.up; } if (vectorJSON.val == "None" && vu_Bool.val == false) { v3 = Vector3.forward; } if (line != null) { Destroy(line); } if (mv_Bool.val) { pastDZx = mvFx.val; pastDZy = mvFy.val; pastDZz = mvFz.val; } else { pastDZx = 1.0f; pastDZy = 1.0f; pastDZz = 1.0f; } if (atomJSON.val != "None" && receiverJSON.val != "None" && en_Bool.val == true) { if (atomJSON.val != "[CameraRig]") { targetAtomPosition = receivingAtom.GetStorableByID(receiverJSON.val).transform.position; } else { if (receiverJSON.val == "CenterEye") { targetAtomPosition = SuperController.singleton.lookCamera.transform.position; } if (receiverJSON.val == "LeftHand") { targetAtomPosition = SuperController.singleton.leftHand.transform.position; } if (receiverJSON.val == "RightHand") { targetAtomPosition = SuperController.singleton.rightHand.transform.position; } } Vector3 adjPosition; adjPosition.x = X.val; adjPosition.y = Y.val; adjPosition.z = Z.val; currentAtomPosition = containingAtom.GetStorableByID("control").transform.position; Vector3 adjcurrentPosition; adjcurrentPosition.x = Xc.val; adjcurrentPosition.y = Yc.val; adjcurrentPosition.z = Zc.val; Vector3 targetDiff; targetDiff = targetAtomPosition - targetPastPosition; if (Mathf.Abs(targetDiff.x) >= tDZx.val) { targetPosition.x = targetPastPosition.x + targetDiff.x * pastDZx; } if (Mathf.Abs(targetDiff.y) >= tDZy.val) { targetPosition.y = targetPastPosition.y + targetDiff.y * pastDZy; } if (Mathf.Abs(targetDiff.z) >= tDZz.val) { targetPosition.z = targetPastPosition.z + targetDiff.z * pastDZz; } if (atomJSON.val == "[CameraRig]" && _isKeepHorToCam.val) { Transform cameraRig = SuperController.singleton.lookCamera.transform; aim = (cameraRig.position + adjPosition) - (cameraRig.forward + adjcurrentPosition) * 10000000.0f; } else { aim = (targetPosition + adjPosition) - (currentAtomPosition + adjcurrentPosition); } look = Quaternion.LookRotation(aim, v3); //containingAtom.GetStorableByID("control").transform.localRotation = look; containingAtom.GetStorableByID("control").transform.rotation = look; if (rev_Bool.val) { Quaternion rev = Quaternion.Euler(0f, 180f, 0f); //containingAtom.GetStorableByID("control").transform.localRotation *= rev; containingAtom.GetStorableByID("control").transform.rotation *= rev; } if (line_Bool.val == true) { if (line != null) { Destroy(line); } line = new GameObject(); var rd = line.AddComponent(); var positions = new Vector3[] { currentAtomPosition + adjcurrentPosition, targetPosition + adjPosition }; rd.startWidth = 0.01f; rd.endWidth = 0.01f; rd.SetPositions(positions); } } targetPastPosition = targetPosition; } catch (Exception e) { SuperController.LogError($"{nameof(Searchlight)}.{nameof(Update)}: {e}"); } } // FixedUpdate is called with each physics simulation frame by Unity void FixedUpdate() { try { // put code in here } catch (Exception e) { SuperController.LogError("Exception caught: " + e); } } public void OnDisable() { try { if (line != null) { Destroy(line); } } catch (Exception e) { SuperController.LogError($"{nameof(Searchlight)}.{nameof(OnDisable)}: {e}"); } } // OnDestroy is where you should put any cleanup // if you registered objects to SuperController or atom, you should unregister them here void OnDestroy() { if (line != null) { Destroy(line); } } } }