/// <summary>
 /// Call this method to subscribe to the specified data service (PLTService enum) from the
 /// device. For example you can subscribe to motion tracking service to receive
 /// head tracking angles etc.
 /// </summary>
 /// <param name="aService">The PLTService enum value defines which service to subscribe to</param>
 /// <param name="aMode">The PLTMode defines On_Change (as soon as new data is available)
 /// or Periodic mode (return data on specific period). Note not all services are compatible
 /// with Periodic mode (These are not: Tap service, Free fall service and Call state service)</param>
 /// <param name="aPeriodmilliseconds">The period in milliseconds to return data
 /// if using Periodic mode</param>
 public void subscribe(PLTService aService, PLTMode aMode, int aPeriodmilliseconds = 0)
 {
     if (m_activeConnection != null)
     {
         m_activeConnection.subscribe(aService, aMode, aPeriodmilliseconds);
     }
     else
     {
         throw new Exception("PLT Labs API subscribe Service: Sorry, you must connect to headset first (see openConnection method)");
     }
 }
Example #2
0
 public PLTServiceSubscription(PLTConnection aConnection, PLTService aService, PLTMode aMode, int aPeriodMilliseconds,
                               object aLastdata = null)
 {
     m_pltconnection      = aConnection;
     m_service            = aService;
     m_mode               = aMode;
     m_periodMilliseconds = aPeriodMilliseconds;
     m_lastData           = aLastdata; // last data or initial value
     if (aMode == PLTMode.Periodic)
     {
         if (aPeriodMilliseconds < 1)
         {
             throw new Exception("Sorry, for periodic service subscription you must specify the period in milliseconds!");
         }
         else
         {
             m_periodTimer          = new Timer();
             m_periodTimer.Interval = aPeriodMilliseconds;
             m_periodTimer.Elapsed += new ElapsedEventHandler(m_periodTimer_Elapsed);
             m_periodTimer.Start();
         }
     }
 }
Example #3
0
        internal void subscribe(PLTService aService, PLTMode aMode, int aPeriodmilliseconds = 0)
        {
            // cannot subscribe to same service twice
            if (isSubscribed(aService))
            {
                return;
            }

            bool   doSubscribe = false;
            object lastData    = null;

            // work out if we can/should subscribe to the service
            switch (aService)
            {
            case PLTService.MOTION_TRACKING_SVC:
                // TODO add to Spokes knowledge of which device
                // has motion tracking. For now just assume all
                // devices do.
                doSubscribe = true;
                break;

            case PLTService.MOTION_STATE_SVC:
                // TODO: does the headset provide this info?
                throw new Exception("Sorry, motion state service is not yet implemented.");
                doSubscribe = false;
                break;

            case PLTService.SENSOR_CAL_STATE_SVC:
                doSubscribe = true;
                break;

            case PLTService.PEDOMETER_SVC:
                doSubscribe = true;
                break;

            case PLTService.TAP_SVC:
                if (aMode == PLTMode.On_Change)
                {
                    doSubscribe = true;
                }
                else
                {
                    throw new Exception("Sorry, tap service only supports PLTMode.On_Change mode (not PLTMode.Periodic).");
                }
                break;

            case PLTService.WEARING_STATE_SVC:
                if (m_spokes.DeviceCapabilities.HasWearingSensor)
                {
                    doSubscribe = true;
                    lock (m_pltlabsapi.m_lastwornstateLock)
                    {
                        lastData = m_pltlabsapi.m_lastwornstate;
                    }
                }
                else
                {
                    throw new Exception("Sorry, device does not have a wearing sensor. Unable to subscribe to wearing sensor data.");
                }
                break;

            case PLTService.FREE_FALL_SVC:
                if (aMode == PLTMode.On_Change)
                {
                    doSubscribe = true;
                }
                else
                {
                    throw new Exception("Sorry, tap service only supports PLTMode.On_Change mode (not PLTMode.Periodic).");
                }
                break;

            case PLTService.PROXIMITY_SVC:
                // Don't bother checking m_spokes.DeviceCapabilities.HasProximity, as this is
                // generally populated with correct value later asyncronously if enable proximity call
                // succeeded
                doSubscribe = true;
                lock (m_pltlabsapi.m_lastproximitystateLock)
                {
                    lastData = m_pltlabsapi.m_lastproximitystate;
                }
                break;

            case PLTService.CALLERID_SVC:
                doSubscribe = true;
                lock (m_pltlabsapi.m_lastcalleridLock)
                {
                    lastData = m_pltlabsapi.m_lastcallerid;
                }
                break;

            case PLTService.CALLSTATE_SVC:
                if (aMode == PLTMode.On_Change)
                {
                    doSubscribe = true;
                    lock (m_pltlabsapi.m_lastcallstateLock)
                    {
                        lastData = m_pltlabsapi.m_lastcallstate;
                    }
                }
                else
                {
                    throw new Exception("Sorry, call state only supports PLTMode.On_Change mode (not PLTMode.Periodic).");
                }
                break;

            case PLTService.DOCKSTATE_SVC:
                doSubscribe = true;
                lock (m_pltlabsapi.m_lastdockstateLock)
                {
                    lastData = m_pltlabsapi.m_lastdockstate;
                }
                break;

            case PLTService.CHARGESTATE_SVC:
                // todo consider not making wireless devices subcribe - no battery
                doSubscribe = true;
                lock (m_pltlabsapi.m_lastbattstateLock)
                {
                    lastData = m_pltlabsapi.m_lastbattstate;
                }
                break;
                //case PLTService.TEMPERATURE_SVC:
                //    doSubscribe = true;
                //    break;
            }

            if (doSubscribe)
            {
                PLTServiceSubscription subscr;
                subscr = new PLTServiceSubscription(this,
                                                    aService, aMode, aPeriodmilliseconds, lastData);
                lock (m_subscribedServicesLock)
                {
                    m_subscribedServices.Add(subscr);
                }

                // NOTE: for SOME services we want to ship the last known value right
                // away to connected app, because for those services such as wearing sensor
                // the last known value will be the "initial" value. (Does not apply to
                // headtracking).
                if (aService == PLTService.WEARING_STATE_SVC ||
                    aService == PLTService.CHARGESTATE_SVC
                    )
                {
                    ShipLastKnownDataToAppForService(aService, subscr);
                }
            }
        }
        /// <summary>
        /// Internal method to send either a subscribe or unsubscribe BladeRunner command
        /// to the BladeRunner device that represents this PLTConnection.
        /// </summary>
        /// <param name="subscribe"></param>
        /// <param name="aService"></param>
        /// <param name="aMode"></param>
        /// <param name="aPeriodmilliseconds"></param>
        private void SendBladeRunnerSubscribeCommand(bool subscribe, PLTService aService, PLTMode aMode = PLTMode.On_Change
                                                     , int aPeriodmilliseconds = 50)
        {
            if (!subscribe)
            {
                aMode = PLTMode.Off;             // unsubscribe!
            }
            switch (aService)
            {
            case PLTService.MOTION_TRACKING_SVC:
                //        Head orientation                0x0000<br/>
                //        Pedometer                       0x0002<br/>
                //        Free Fall                       0x0003<br/>
                //        Taps                            0x0004<br/>
                //        Magnetometer Calibration Status 0x0005<br/>
                //        Gyroscope Calibration Status    0x0006<br/>
                //        Versions                        0x0007<br/>
                //        Humidity                        0x0008<br/>
                //        Light                           0x0009<br/>
                //        Optical proximity               0x0010<br/>
                //        Ambient Temp 1                  0x0011<br/>
                //        Ambient Temp 2                  0x0012<br/>
                //        Skin Temp                       0x0013<br/>
                //        Skin Conductivity               0x0014<br/>
                //        Ambient Pressure                0x0015<br/>
                //        Heart Rate                      0x0016<br/>
                //The update mode for the service.<br/>
                //    0 = off,<br/>
                //    1 = on-change,<br/>
                //    2 = periodic<br/>
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceSensorService(m_device.m_device, 0,
                                                                (int)aMode, aPeriodmilliseconds);
                }
                break;

            case PLTService.PEDOMETER_SVC:
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceSensorService(m_device.m_device, 2,
                                                                (int)aMode, aPeriodmilliseconds);
                }
                break;

            case PLTService.FREE_FALL_SVC:
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceSensorService(m_device.m_device, 3,
                                                                (int)aMode, aPeriodmilliseconds);
                }
                break;

            case PLTService.TAP_SVC:
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceSensorService(m_device.m_device, 4,
                                                                (int)aMode, aPeriodmilliseconds);
                }
                break;

            case PLTService.SENSOR_CAL_STATE_SVC:
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceSensorService(m_device.m_device, 5,
                                                                (int)aMode, aPeriodmilliseconds);
                }
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceSensorService(m_device.m_device, 6,
                                                                (int)aMode, aPeriodmilliseconds);
                }
                break;

            case PLTService.WEARING_STATE_SVC:
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceWearingStateService(m_pltlabsapi.m_wearingsensorDevice.m_device, true);
                }
                break;

            case PLTService.PROXIMITY_SVC:
                if (m_pltlabsapi != null)
                {
                    m_pltlabsapi.RegisterForDeviceProximityService(m_pltlabsapi.m_proximityDevice.m_device, true);
                }
                break;
            }
        }