private void registerTrackedDeviceFeedback(AirVRTrackedDeviceFeedback feedback)
    {
        int    cookieTextureSize = Marshal.SizeOf(feedback.cookieTexture[0]) * feedback.cookieTexture.Length;
        IntPtr ptr = Marshal.AllocHGlobal(cookieTextureSize);

        Marshal.Copy(feedback.cookieTexture, 0, ptr, feedback.cookieTexture.Length);
        feedback.OnRegistered(onairvr_RegisterTrackedDeviceFeedbackAsInputSender(owner.playerID, feedback.name, ptr, cookieTextureSize, feedback.cookieDepthScaleMultiplier));

        Marshal.FreeHGlobal(ptr);
    }
    public void FeedbackTrackedDevice(string deviceName, byte controlID, Vector3 rayOrigin, Vector3 hitPosition, Vector3 hitNormal)
    {
        if (senders.ContainsKey(deviceName))
        {
            AirVRTrackedDeviceFeedback feedback = senders[deviceName] as AirVRTrackedDeviceFeedback;
            Assert.IsNotNull(feedback);

            feedback.SetRaycastResult(rayOrigin, hitPosition, hitNormal);
        }
    }
    public override void Init()
    {
        Assert.IsTrue(owner != null && owner.isBoundToClient);

        foreach (var key in senders.Keys)
        {
            AirVRTrackedDeviceFeedback feedback = senders[key] as AirVRTrackedDeviceFeedback;
            Assert.IsNotNull(feedback);

            registerTrackedDeviceFeedback(feedback);
        }

        base.Init();
    }
 public void EnableTrackedDeviceFeedback(string deviceName, Texture2D cookieTexture, float cookieDepthScaleMultiplier)
 {
     if (senders.ContainsKey(deviceName) == false)
     {
         AirVRTrackedDeviceFeedback feedback = createTrackedDeviceFeedback(deviceName, cookieTexture, cookieDepthScaleMultiplier);
         if (feedback != null)
         {
             addDeviceFeedback(feedback);
             if (owner != null && owner.isBoundToClient)
             {
                 registerTrackedDeviceFeedback(feedback);
             }
         }
     }
 }