Timer code always runs in the main thread during idle time. Other threads running won’t affect that, so yes, no matter where the Timer is activated, it’s entirely possible that it will run before your thread is finished.
In fact, that how a thread can manipulate the UI indirectly. You put the changes into a properties, then call the method that updates the UI from a Timer started by the thread.
Yes. I just ran into this. Interestingly with the same (high) priority assigned to the thread, the effect was much more pronounced on Windows than Mac.
Think a main thread as just another thread when it comes to synchronization between threads, but just never make it very busy to avoid UI problems. For your problem of “waiting for threads”, you can use inter-threads synchronizing methods like CriticalSection.TryEnter() or Semaphore.TrySignal() to check for some task condition flagged in another thread like “the thread ended his last job and is waiting”.
Also you can do some tricks too, like inside the thread calling Suspend() to signalize some stop condition and checking for ThatThread.State = 2 in the main thread. Then releasing it later with thatThread.Resume() later to do another loop or end.