[성현모] CPXV2 Init

This commit is contained in:
SHM
2024-06-26 10:30:00 +09:00
parent cdf12248c5
commit 5958993b6a
588 changed files with 698420 additions and 0 deletions

View File

@ -0,0 +1,158 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics.Contracts;
using System.Linq;
using System.Reactive.Linq;
using System.Reactive.Subjects;
using System.Runtime.InteropServices;
using System.Windows.Forms;
namespace SystemX.Net.Platform.Common.Event
{
public interface ISysXEventField : ISynchronizeInvoke
{
void ProcessEvent(IObservableEvent evt);
}
public class OSCAREventHandler : ISubscribable
{
public Subject<IObservableEvent> ApplicationSubject = new Subject<IObservableEvent>();
protected List<IDisposable> _applicationSubscriptions = new List<IDisposable>();
public ISysXEventField TheApplicationTarget { get; set; }
public static OSCAREventHandler TheApplication { get; private set; }
public OSCAREventHandler(ISysXEventField eventField)
{
Contract.Requires(eventField is Form);
Contract.Requires(TheApplication == null);
TheApplication = this;
TheApplicationTarget = eventField;
var observable = Observable
.Interval(TimeSpan.FromSeconds(1))
.Take(5);
var observer = System.Reactive.Observer.Create<long>(
x => Console.WriteLine("Value published to subject #1: {0}", x),
() => Console.WriteLine("Sequence Completed."));
AddSubscription(ApplicationSubject.Subscribe(evt => OnApplicationEvent(evt)));
}
/// <summary>
/// Applicatino event 처리.
/// Note: ObservableEventTask{Starting, Finished} 는 별도 subscription 을 통해서 처리 됨.
/// </summary>
/// <param name="evt"></param>
private void OnApplicationEvent(IObservableEvent evt)
{
// 샘플 코드
bool onMainThread = !TheApplicationTarget.InvokeRequired;
//System.Media.SystemSounds.Beep.Play();
// thread 상에서 호출되었다면, main UI thread 상에서 수행되도록 한다.
//TheApplicationForm.Do(() =>
//{
//logger.Info($"Application got event : {evt}");
//((IOSCAREventField)TheApplicationForm).HandleStationEvent(evt);
ProcessObservableEventHandler(evt);
//});
}
protected delegate void ObservableEventHandler(IObservableEvent evt);
private void ProcessObservableEventHandler(IObservableEvent evt)
{
if (TheApplicationTarget.InvokeRequired)
{
ObservableEventHandler delState = new ObservableEventHandler(ProcessObservableEventHandler);
(TheApplicationTarget as Control).Invoke(delState, evt);
}
else
{
TheApplicationTarget.ProcessEvent(evt);
}
}
public void AddSubscription(IDisposable subscription)
{
_applicationSubscriptions.Add(subscription);
}
public void Dispose()
{
Dispose(true); // true : 명시적 dispose 호출
GC.SuppressFinalize(this); // 사용자에 의해서 명시적으로 dispose 되었으므로, GC 는 이 객체에 대해서 손대지 말것을 알림.
}
private bool _disposed;
protected virtual void Dispose(bool disposing)
{
if (_disposed)
return;
if (disposing)
{
// AwaitTermination() call hangs. Need to check Akka document.
// CommonApplication.ActorSystem.AwaitTermination();
_applicationSubscriptions.ForEach(s => s.Dispose());
}
_disposed = true;
}
}
public class TestEvent : IObservableEvent
{
public string Process { private set; get; }
public string Path { set; get; }
public TestEvent(string process, string strPath)
{
Process = process;
Path = strPath;
}
}
/// <summary>
/// Rx event 에 대한 subscribe 가 가능한 객체가 구현해야 할 interface
/// Dispose 시에 모든 subscription 을 dispose 해야 한다.
/// </summary>
public interface ISubscribable : IDisposable
{
/* Usage sample
private List<IDisposable> _subscriptions = new List<IDisposable>();
public void AddSubscription(IDisposable subscription) { _subscriptions.Add(subscription); }
// Requires disposal of subscriptions on Dispose() method
*
*/
void AddSubscription(IDisposable subscription);
}
/// <summary> Configuration interface </summary>
[Guid("8501C86A-61E7-4F92-B90A-1779CCF6AAF3")]
[InterfaceType(ComInterfaceType.InterfaceIsDual)]
[ComVisible(true)]
public interface IConfiguration : ICloneable
{
/// <summary> Save configuration to file </summary>
void QSave(string fileName);
/// <summary> Load configuration from file </summary>
void QLoad(string fileName);
}
/// <summary>
/// Rx: System.Reactive.Subjects.Subject 에 대한 base interface
/// </summary>
[ComVisible(false)]
public interface IObservableEvent
{
}
public interface IObservableUIEvent : IObservableEvent { }
}

View File

@ -0,0 +1,22 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SystemX.Net.Platform.Common.Event
{
public class FunctionEventHandler
{
public FunctionEventHandler() { }
public delegate void evtReceiveHandler(object sender, object data);
public event evtReceiveHandler OnReceive;
public void DoReceive(object sender, object data)
{
if (OnReceive != null)
OnReceive(sender, data);
}
}
}

View File

@ -0,0 +1,63 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
namespace SystemX.Net.Platform.Common.Event
{
public class PauseTokenSource
{
private volatile TaskCompletionSource<bool> m_paused;
internal static readonly Task s_completedTask = Task.FromResult(true);
public void Pause()
{
Interlocked.CompareExchange(
ref m_paused, new TaskCompletionSource<bool>(), null);
}
public void Resume()
{
while (true)
{
var tcs = m_paused;
if (tcs == null) return;
if (Interlocked.CompareExchange(ref m_paused, null, tcs) == tcs)
{
tcs.SetResult(true);
break;
}
}
}
public bool IsPaused
{
get { return m_paused != null; }
}
public PauseToken Token { get { return new PauseToken(this); } }
internal Task WaitWhilePausedAsync()
{
var cur = m_paused;
return cur != null ? cur.Task : s_completedTask;
}
}
public struct PauseToken
{
private readonly PauseTokenSource m_source;
internal PauseToken(PauseTokenSource source) { m_source = source; }
public bool IsPaused { get { return m_source != null && m_source.IsPaused; } }
public Task WaitWhilePausedAsync()
{
return IsPaused ?
m_source.WaitWhilePausedAsync() :
PauseTokenSource.s_completedTask;
}
}
}