﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Threading;


namespace PythonPlot
{
  /// <summary>
  /// This class provide a Start and a Stop method that you can override to implement your own
  /// thread class.
  /// </summary>
  public abstract class RunAbleThread
  {
    private readonly Thread _runnerThread;

    protected RunAbleThread()
    {
      // we need to create a thread instead of calling Run() directly because it would block unity
      // from doing other tasks like drawing game scenes
      _runnerThread = new Thread(Run);
    }

    /// <summary>
    /// As long as this method returns true, the Run method will continue to run. 
    /// This check has to be implemented by the derived class Run method.
    /// </summary>
    protected bool Running { get; private set; }

    /// <summary>
    /// This method will get called when you call Start(). Programmer must implement this method while making sure that
    /// this method terminates in a finite time. You can use Running property (which will be set to false when Stop() is
    /// called) to determine when you should stop the method.
    /// </summary>
    protected abstract void Run();

    /// <summary>
    /// Start the thread by executing the overriden Run method
    /// </summary>
    public void Start()
    {
      Running = true;
      _runnerThread.Start();
    }

    /// <summary>
    /// Stop the running thread.
    /// </summary>
    virtual public void Stop()
    {
      Running = false;
      // block main thread, wait for _runnerThread to finish its job first, so we can be sure that 
      // _runnerThread will end before main thread end
      _runnerThread.Join();
    }
  }


}
