2

My Requirement : Need a session timer for every page(Except login page). If timer exceeded 60 seconds with no user actions performed, it should redirect to the login page.

I have successfully done the above requirement for one page with below code snippets.

        DispatcherTimer dispatcherTimer;
        DateTimeOffset startTime;
        DateTimeOffset lastTime;
        DateTimeOffset stopTime;
        int timesTicked = 1;
        int timesToTick = 60; 


        page_load()
        {  
           dispatcherTimer = new DispatcherTimer();
           dispatcherTimer.Tick += dispatcherTimer_Tick;
           dispatcherTimer.Interval = new TimeSpan(0, 0, 1);
           startTime = DateTimeOffset.Now;
           lastTime = startTime;
           dispatcherTimer.Start();    
        } 


        private void PhoneApplicationPage_ManipulationCompleted(object sender, System.Windows.Input.ManipulationCompletedEventArgs e)
        {
            startTime = DateTimeOffset.Now;
            lastTime = startTime;
            dispatcherTimer.Start();    
        }

       void dispatcherTimer_Tick(object sender, object e)
       {
           DateTimeOffset time = DateTimeOffset.Now;
           TimeSpan span = time - lastTime;
           lastTime = time;
           timesTicked++;
           if (timesTicked > timesToTick)
           {
               isTimeOver = true;
               stopTime = time;

               dispatcherTimer.Stop();

               span = stopTime - startTime;
               MessageBox.Show("Login again", "Session Expired", MessageBoxButton.OK);
               NavigationService.Navigate(new Uri("/Login_3.xaml", UriKind.Relative)); 
           }
       }

I need this logic for every pages. As pages are not accessible in custom classes for navigation, I am confused. I don't think writing dispatcherTimer_Tick event in every page is good approach. Could you please anyone advice how we can do this in one code that can be used for every page? Thanks in advance:)

Bells
  • 1,465
  • 1
  • 19
  • 30
Ramin
  • 71
  • 1
  • 4

1 Answers1

0

You can create a common base class for each page to inherit from and write this code there.

Example:

namespace Test
{     
    public class PageBaseWithTimer: PhoneApplicationPage
    {
        DispatcherTimer dispatcherTimer;

        ... //Copied from question

        int timesToTick = 60; 

        PageBase()
        {
            this.Loaded += PageBase_Loaded;
            this.OnManipulationCompleted += PhoneApplicationPage_ManipulationCompleted
        }

        private void PageBase_Loaded(object sender, RoutedEventArgs e)
        {
             dispatcherTimer = new DispatcherTimer();

             ... //Copied from question

             dispatcherTimer.Start();
        }

        private void PhoneApplicationPage_ManipulationCompleted(object sender, System.Windows.Input.ManipulationCompletedEventArgs e)
        {
            startTime = DateTimeOffset.Now;
            lastTime = startTime;
            dispatcherTimer.Start();  
        }      

        void dispatcherTimer_Tick(object sender, object e)
        {
            DateTimeOffset time = DateTimeOffset.Now;

            ... //Copied from question

            MessageBox.Show("Login again", "Session Expired", MessageBoxButton.OK);
            NavigationService.Navigate(new Uri("/Login_3.xaml", UriKind.Relative)); 
        }

        protected override void OnNavigatedFrom(System.Windows.Navigation.NavigationEventArgs args)
        {
            //dispose timer
            dispatcherTimer.Stop();
            dispatcherTime.Tick -= dispatcherTimer_Tick
            dispatcherTimer = null;
        }
    }
}

Inherit the above class in the pages where you require this timer. Remember to dispose timer in base class if its not required, while navigating away.

    public partial class PageWithTimer1 : PageBaseWithTimer
    { 
        public PageWithTimer1()
        {
            InitializeComponent();
        }           
    }

   <c:PageBaseWithTimer xmlns:c="clr-namespace:Test"
        x:Class="BBM.UI.Views.PageWithTimer1" 
        ...

   </c:PageBaseWithTimer>

Make sure you give the access modifier as public for the base class - PageBaseWithTimer, to make it available across all pages.

Bells
  • 1,465
  • 1
  • 19
  • 30
  • Thanks for your reply. I have tried like this, But i got an error like The name "PageBaseWithTimer" does not exist in the namespace "clr-namespace:TEST" Could you please elaborate the second code snippet? – Ramin Feb 14 '17 at 03:57