Exemple #1
0
        /// <summary>
        /// Create a new <see cref="PrecisionInputTimer"/> class.
        /// </summary>
        /// <param name="framesPerSecond">Desired frame rate for <see cref="PrecisionTimer"/>.</param>
        internal PrecisionInputTimer(int framesPerSecond)
        {
            // Create synchronization objects
            m_timerTickLock = new SpinLock();
            m_frameWaitHandleA = new ManualResetEventSlim(false);
            m_frameWaitHandleB = new ManualResetEventSlim(false);
            m_useWaitHandleA = true;
            m_framesPerSecond = framesPerSecond;

            // Create a new precision timer for this timer state
            m_timer = new PrecisionTimer();
            m_timer.Resolution = 1;
            m_timer.Period = 1;
            m_timer.AutoReset = true;

            // Attach handler for timer ticks
            m_timer.Tick += m_timer_Tick;

            m_frameWindowSize = (int)Math.Round(1000.0D / framesPerSecond) * 2;
            m_frameMilliseconds = new int[framesPerSecond];

            for (int frameIndex = 0; frameIndex < framesPerSecond; frameIndex++)
            {
                m_frameMilliseconds[frameIndex] = (int)(1.0D / framesPerSecond * (frameIndex * 1000.0D));
            }

            // Start high resolution timer on a separate thread so the start
            // time can synchronized to the top of the millisecond
            ThreadPool.QueueUserWorkItem(SynchronizeInputTimer);
        }
Exemple #2
0
            /// <summary>
            /// Releases the unmanaged resources used by the <see cref="FrameRateTimer"/> object and optionally releases the managed resources.
            /// </summary>
            /// <param name="disposing">true to release both managed and unmanaged resources; false to release only unmanaged resources.</param>
            private void Dispose(bool disposing)
            {
                if (!m_disposed)
                {
                    try
                    {
                        if (disposing)
                        {
                            if (m_timer != null)
                            {
                                if (m_processingInterval == -1)
                                    m_timer.Tick -= SetTimerPeriod;

                                m_timer.Dispose();
                            }
                            m_timer = null;
                        }
                    }
                    finally
                    {
                        m_disposed = true;  // Prevent duplicate dispose.
                    }
                }
            }
Exemple #3
0
            /// <summary>
            /// Create a new <see cref="FrameRateTimer"/> class.
            /// </summary>
            /// <param name="framesPerSecond">Desired frame rate for <see cref="PrecisionTimer"/>.</param>
            /// <param name="processingInterval">Desired processing interval, if applicable.</param>
            /// <remarks>
            /// When the <paramref name="processingInterval"/> is set to -1, the frame rate timer interval will be calculated as a distribution
            /// of whole milliseonds over the specified number of <paramref name="framesPerSecond"/>. Otherwise the specified
            /// <paramref name="processingInterval"/> will be used as the timer interval.
            /// </remarks>
            public FrameRateTimer(int framesPerSecond, int processingInterval)
            {
                if (processingInterval == 0)
                    throw new InvalidOperationException("A frame rate timer should not be created when using a processing interval of zero, i.e., processing data as fast as possible.");

                m_framesPerSecond = framesPerSecond;
                m_processingInterval = processingInterval;

                // Create a new precision timer for this timer state
                m_timer = new PrecisionTimer();
                m_timer.AutoReset = true;

                if (processingInterval > 0)
                {
                    // Establish fixed timer period
                    m_timer.Period = processingInterval;
                }
                else
                {
                    // Attach handler for timer period assignments
                    m_timer.Tick += SetTimerPeriod;

                    // Calculate distributed wait time periods over specified number of frames per second
                    m_framePeriods = new int[framesPerSecond];

                    for (int frameIndex = 0; frameIndex < framesPerSecond; frameIndex++)
                    {
                        m_framePeriods[frameIndex] = CalcWaitTimeForFrameIndex(frameIndex);
                    }

                    // Establish initial timer period
                    m_lastFramePeriod = m_framePeriods[0];
                    m_timer.Period = m_lastFramePeriod;
                }

                // Start timer
                m_timer.Start();
            }
Exemple #4
0
        /// <summary>
        /// Releases the unmanaged resources used by the <see cref="ConcentratorBase"/> object and optionally releases the managed resources.
        /// </summary>
        /// <param name="disposing">true to release both managed and unmanaged resources; false to release only unmanaged resources.</param>
        protected virtual void Dispose(bool disposing)
        {
            if (!m_disposed)
            {
                try
                {
                    if (disposing)
                    {
                        if (m_publicationTimer != null)
                        {
                            m_publicationTimer.Tick -= PublishFrames;
                            m_publicationTimer.Dispose();
                        }
                        m_publicationTimer = null;

                        if (m_frameQueue != null)
                        {
                            m_frameQueue.Dispose();
                        }
                        m_frameQueue = null;

                        if (m_monitorTimer != null)
                        {
                            m_monitorTimer.Elapsed -= MonitorUnpublishedSamples;
                            m_monitorTimer.Dispose();
                        }
                        m_monitorTimer = null;

                        if (m_latestMeasurements != null)
                        {
                            m_latestMeasurements.Dispose();
                        }
                        m_latestMeasurements = null;

                        m_lastDiscardedMeasurement = null;
                    }
                }
                finally
                {
                    m_disposed = true;  // Prevent duplicate dispose.
                }
            }
        }
Exemple #5
0
        private bool m_disposed;                            // Disposed flag detects redundant calls to dispose method

        #endregion

        #region [ Constructors ]

        /// <summary>
        /// Creates a new <see cref="ConcentratorBase"/>.
        /// </summary>
        /// <param name="framesPerSecond">Number of frames to publish per second.</param>
        /// <param name="lagTime">Past time deviation tolerance, in seconds - this becomes the amount of time to wait before publishing begins.</param>
        /// <param name="leadTime">Future time deviation tolerance, in seconds - this becomes the tolerated +/- accuracy of the local clock to real-time.</param>
        /// <remarks>
        /// <para>
        /// <paramref name="framesPerSecond"/> must be between 1 and 1000.
        /// </para>
        /// <para>
        /// <paramref name="lagTime"/> must be greater than zero, but can be specified in sub-second intervals (e.g., set to .25 for a quarter-second lag time).
        /// Note that this defines time sensitivity to past timestamps.
        /// </para>
        /// <para>
        /// <paramref name="leadTime"/> must be greater than zero, but can be specified in sub-second intervals (e.g., set to .5 for a half-second lead time).
        /// Note that this defines time sensitivity to future timestamps.
        /// </para>
        /// <para>
        /// Concentration will not begin until consumer "Starts" concentrator (i.e., calling <see cref="ConcentratorBase.Start"/> method or setting
        /// <c><see cref="ConcentratorBase.Enabled"/> = true</c>).
        /// </para>
        /// </remarks>
        /// <exception cref="ArgumentOutOfRangeException">Specified argument is outside of allowed value range (see remarks).</exception>
        protected ConcentratorBase(int framesPerSecond, double lagTime, double leadTime)
        {
            if (lagTime <= 0)
                throw new ArgumentOutOfRangeException("lagTime", "lagTime must be greater than zero, but it can be less than one");

            if (leadTime <= 0)
                throw new ArgumentOutOfRangeException("leadTime", "leadTime must be greater than zero, but it can be less than one");

            this.FramesPerSecond = framesPerSecond;

#if UseHighResolutionTime
            m_realTimeTicks = PrecisionTimer.UtcNow.Ticks;
#else
            m_realTime = DateTime.UtcNow.Ticks;
#endif
            m_allowSortsByArrival = true;
            m_lagTime = lagTime;
            m_leadTime = leadTime;
            m_lagTicks = (long)(m_lagTime * Ticks.PerSecond);
            m_latestMeasurements = new ImmediateMeasurements(this);

            // Create a new queue for managing real-time frames
            m_frameQueue = new FrameQueue(this);

            // Create high precision timer used for frame processing
            m_publicationTimer = new PrecisionTimer();
            m_publicationTimer.AutoReset = true;
            m_publicationTimer.Tick += PublishFrames;

            // This timer monitors the total number of unpublished samples every second. This is a useful statistic
            // to monitor: if total number of unpublished samples exceed lag time, measurement concentration could
            // be falling behind.
            m_monitorTimer = new System.Timers.Timer();
            m_monitorTimer.Interval = 1000;
            m_monitorTimer.AutoReset = true;
            m_monitorTimer.Elapsed += MonitorUnpublishedSamples;
        }
Exemple #6
0
        // Protected Methods

        /// <summary>Shuts down concentrator in an orderly fashion.</summary>
        protected virtual void Dispose(bool disposing)
        {
            if (!m_disposed)
            {
                if (disposing)
                {
                    if (m_publicationTimer != null)
                    {
                        m_publicationTimer.Tick -= PublishFrames;
                        m_publicationTimer.Dispose();
                    }
                    m_publicationTimer = null;

                    if (m_frameQueue != null)
                    {
                        m_frameQueue.Dispose();
                    }
                    m_frameQueue = null;

                    if (m_monitorTimer != null)
                    {
                        m_monitorTimer.Elapsed -= MonitorUnpublishedSamples;
                        m_monitorTimer.Dispose();
                    }
                    m_monitorTimer = null;

                    if (m_latestMeasurements != null)
                    {
                        m_latestMeasurements.Dispose();
                    }
                    m_latestMeasurements = null;
                }
            }

            m_disposed = true;
        }
Exemple #7
0
 /// <summary>
 /// Releases the unmanaged resources used by the <see cref="FrameRateTimer"/> object and optionally releases the managed resources.
 /// </summary>
 /// <param name="disposing">true to release both managed and unmanaged resources; false to release only unmanaged resources.</param>
 protected virtual void Dispose(bool disposing)
 {
     if (!m_disposed)
     {
         try
         {
             if (disposing)
             {
                 if (m_timer != null)
                 {
                     m_timer.Tick -= SetTimerPeriod;
                     m_timer.Dispose();
                 }
                 m_timer = null;
             }
         }
         finally
         {
             m_disposed = true;  // Prevent duplicate dispose.
         }
     }
 }
Exemple #8
0
            /// <summary>
            /// Create a new <see cref="FrameRateTimer"/> class.
            /// </summary>
            /// <param name="framesPerSecond">Desired frame rate for <see cref="PrecisionTimer"/>.</param>
            public FrameRateTimer(int framesPerSecond)
            {
                // Create a new precision timer for this timer state
                m_timer = new PrecisionTimer();
                m_timer.AutoReset = true;

                // Attach handler for timer period assignments
                m_timer.Tick += SetTimerPeriod;

                m_framesPerSecond = framesPerSecond;
                m_framePeriods = new int[framesPerSecond];

                // Calculate new wait time periods for new number of frames per second
                for (int frameIndex = 0; frameIndex < framesPerSecond; frameIndex++)
                {
                    m_framePeriods[frameIndex] = CalcWaitTimeForFrameIndex(frameIndex);
                }

                // Establish initial timer period
                m_lastFramePeriod = m_framePeriods[0];
                m_timer.Period = m_lastFramePeriod;

                // Start timer
                m_timer.Start();
            }
Exemple #9
0
        /// <summary>
        /// Releases the unmanaged resources used by the <see cref="PrecisionInputTimer"/> object and optionally releases the managed resources.
        /// </summary>
        /// <param name="disposing">true to release both managed and unmanaged resources; false to release only unmanaged resources.</param>
        private void Dispose(bool disposing)
        {
            if (!m_disposed)
            {
                try
                {
                    if (disposing)
                    {
                        if (m_timer != null)
                        {
                            m_timer.Tick -= m_timer_Tick;
                            m_timer.Dispose();
                        }
                        m_timer = null;

                        if (m_frameWaitHandleA != null)
                        {
                            m_frameWaitHandleA.Set();
                            m_frameWaitHandleA.Dispose();
                        }
                        m_frameWaitHandleA = null;

                        if (m_frameWaitHandleB != null)
                        {
                            m_frameWaitHandleB.Set();
                            m_frameWaitHandleB.Dispose();
                        }
                        m_frameWaitHandleB = null;
                    }
                }
                finally
                {
                    m_disposed = true;  // Prevent duplicate dispose.
                }
            }
        }