using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
namespace NTwain
{
///
/// Allows work to be marshalled to a different (usually UI) thread if necessary.
///
public interface IThreadMarshaller
{
///
/// Starts work asynchronously and returns immediately.
///
///
void BeginInvoke(Delegate work, params object[] args);
///
/// Starts work synchronously until it returns.
///
///
///
///
object Invoke(Delegate work, params object[] args);
}
///
/// Doesn't actually use any particular thread.
/// Should only be used in non-UI apps.
///
public class NoParticularMarshaller : IThreadMarshaller
{
public bool InvokeRequired => throw new NotImplementedException();
public void BeginInvoke(Delegate work, params object[] args)
{
Task.Run(() => work.DynamicInvoke(args));
}
public object Invoke(Delegate work, params object[] args)
{
return work.DynamicInvoke(args);
}
}
///
/// Uses a winform UI thread to do the work.
///
public class WinformMarshaller : IThreadMarshaller
{
private readonly System.Windows.Forms.Control _uiControl;
///
/// Uses a control whose UI thread is used to run the work.
///
///
public WinformMarshaller(System.Windows.Forms.Control uiControl)
{
_uiControl = uiControl ?? throw new ArgumentNullException(nameof(uiControl));
}
public void BeginInvoke(Delegate work, params object[] args)
{
_uiControl.BeginInvoke(work, args);
}
public object Invoke(Delegate work, params object[] args)
{
return _uiControl.Invoke(work, args);
}
}
///
/// Uses a WPF dispatcher to do the work.
///
public class DispatcherMarshaller : IThreadMarshaller
{
private readonly System.Windows.Threading.Dispatcher _dispatcher;
///
/// Uses a dispatcher whose UI thread is used to run the work.
///
///
public DispatcherMarshaller(System.Windows.Threading.Dispatcher dispatcher)
{
_dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher));
}
public void BeginInvoke(Delegate work, params object[] args)
{
_dispatcher.BeginInvoke(work, args);
}
public object Invoke(Delegate work, params object[] args)
{
return _dispatcher.Invoke(work, args);
}
}
}