[성현모] CPXV2 Init
This commit is contained in:
@ -0,0 +1,427 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.Drawing;
|
||||
using System.Linq;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using System.Windows.Forms;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
|
||||
namespace SystemX.Net.Platform.Common.ExtensionMethods
|
||||
{
|
||||
/// <summary>
|
||||
/// http://lostechies.com/derickbailey/2011/01/24/asynchronous-control-updates-in-c-net-winforms/
|
||||
/// </summary>
|
||||
public static class EmControl
|
||||
{
|
||||
public static void Do<TControl>(this TControl control, Action<TControl> action)
|
||||
where TControl : Control
|
||||
{
|
||||
try
|
||||
{
|
||||
if (control.InvokeRequired)
|
||||
{
|
||||
try
|
||||
{
|
||||
control.Invoke(action, control);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
if (ex is ObjectDisposedException)
|
||||
Trace.WriteLine(ex);
|
||||
else
|
||||
throw;
|
||||
}
|
||||
}
|
||||
else if (control.IsHandleCreated)
|
||||
action(control);
|
||||
else
|
||||
{
|
||||
Console.WriteLine("Error : Before windows handle created.. 창 핸들을 만들기 전까지는....");
|
||||
Trace.WriteLine("Error : Before windows handle created.. 창 핸들을 만들기 전까지는....");
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Trace.WriteLine($"Exception on Control.Do(): {ex}");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Control.Invoke is synchronous
|
||||
/// </summary>
|
||||
/// <param name="control"></param>
|
||||
/// <param name="action"></param>
|
||||
public static void Do(this Control control, Action action)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (control.InvokeRequired)
|
||||
{
|
||||
try
|
||||
{
|
||||
control.Invoke(action);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
if (ex is ObjectDisposedException)
|
||||
Trace.WriteLine(ex);
|
||||
else
|
||||
throw;
|
||||
}
|
||||
}
|
||||
else if (control.IsHandleCreated)
|
||||
action();
|
||||
else
|
||||
{
|
||||
Console.WriteLine("Error : Before windows handle created (2).. 창 핸들을 만들기 전까지는....");
|
||||
Trace.WriteLine("Error : Before windows handle created (2).. 창 핸들을 만들기 전까지는....");
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Trace.WriteLine($"Exception on Control.Do(): {ex}");
|
||||
}
|
||||
}
|
||||
|
||||
public static void Do(this SynchronizationContext context, Action action)
|
||||
{
|
||||
context.Send(ignore => { action(); }, null);
|
||||
}
|
||||
public static void DoAsync(this SynchronizationContext context, Action action)
|
||||
{
|
||||
context.Post(ignore => { action(); }, null);
|
||||
}
|
||||
|
||||
public static SynchronizationContext GetSynchronizationContext(this Control control)
|
||||
{
|
||||
SynchronizationContext context = null;
|
||||
control.Do(() =>
|
||||
{
|
||||
context = SynchronizationContext.Current;
|
||||
});
|
||||
|
||||
return context;
|
||||
}
|
||||
|
||||
public static TaskScheduler GetTaskScheduler(this Control control)
|
||||
{
|
||||
TaskScheduler scheduler = null;
|
||||
control.Do(() =>
|
||||
{
|
||||
scheduler = TaskScheduler.FromCurrentSynchronizationContext();
|
||||
});
|
||||
|
||||
return scheduler;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// form 에 대해서, 아직 창 핸들이 만들어 지지 않은 경우, form 이 보여진 후에 해당 action 을 수행한다.
|
||||
/// </summary>
|
||||
/// <param name="form"></param>
|
||||
/// <param name="action"></param>
|
||||
public static void DoNowOrLater(this Form form, Action action)
|
||||
{
|
||||
if (form.InvokeRequired)
|
||||
form.Invoke(action);
|
||||
else if (form.IsHandleCreated)
|
||||
action();
|
||||
else
|
||||
form.Shown += (sender, args) => { action(); };
|
||||
}
|
||||
|
||||
public static async Task DoAsync(this Control control, Action action)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (control.InvokeRequired)
|
||||
await Task.Factory.FromAsync(control.BeginInvoke(action), result => { });
|
||||
else if (control.IsHandleCreated)
|
||||
action();
|
||||
else
|
||||
Console.WriteLine("Error : 창 핸들을 만들기 전까지는....");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Trace.WriteLine($"Exception on Control.Do(): {ex}");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// How to get return value when BeginInvoke/Invoke is called in C#
|
||||
/// http://stackoverflow.com/questions/2214002/how-to-get-return-value-when-begininvoke-invoke-is-called-in-c-sharp
|
||||
/// </summary>
|
||||
public static T DoGet<T>(this Control control, Func<T> func)
|
||||
{
|
||||
if (control.InvokeRequired)
|
||||
return (T)control.Invoke(func);
|
||||
|
||||
return func();
|
||||
}
|
||||
|
||||
public static IEnumerable<Control> CollectAncestors(this Control control, bool includeMe = false)
|
||||
{
|
||||
if (includeMe)
|
||||
yield return control;
|
||||
if (control == null || control.Parent == null)
|
||||
yield break;
|
||||
|
||||
foreach (var ancestor in control.Parent.CollectAncestors(true))
|
||||
yield return ancestor;
|
||||
}
|
||||
|
||||
public static IEnumerable<Control> CollectAncestorsTo(this Control control, Control stopAncestorControl,
|
||||
bool includeMe = false)
|
||||
{
|
||||
if (includeMe)
|
||||
yield return control;
|
||||
|
||||
if (control == stopAncestorControl || control.Parent == null)
|
||||
yield break;
|
||||
|
||||
foreach (var ancestor in control.Parent.CollectAncestorsTo(stopAncestorControl, true))
|
||||
yield return ancestor;
|
||||
}
|
||||
|
||||
|
||||
public static IEnumerable<Control> CollectChildren(this Control control, bool includeMe = false)
|
||||
{
|
||||
if (includeMe)
|
||||
yield return control;
|
||||
|
||||
foreach (var child in control.Controls.Cast<Control>())
|
||||
{
|
||||
foreach (var descendant in child.CollectChildren(true))
|
||||
yield return descendant;
|
||||
}
|
||||
|
||||
if (control is TabControl)
|
||||
{
|
||||
var tab = (TabControl) control;
|
||||
foreach (var page in tab.TabPages.Cast<TabPage>())
|
||||
{
|
||||
foreach (var descendant in page.CollectChildren(true))
|
||||
{
|
||||
yield return descendant;
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static IEnumerable<T> CollectChildren<T>(this Control control, bool includeMe = false) where T : Control
|
||||
{
|
||||
return control.CollectChildren(includeMe).OfType<T>();
|
||||
|
||||
//if (includeMe && control is T)
|
||||
// yield return control as T;
|
||||
|
||||
//foreach (var child in control.Controls.Cast<Control>())
|
||||
//{
|
||||
// foreach (var descendant in child.CollectChildren<T>(true))
|
||||
// yield return descendant;
|
||||
//}
|
||||
|
||||
//if (control is TabControl)
|
||||
//{
|
||||
// var tab = (TabControl)control;
|
||||
// foreach (var page in tab.TabPages.Cast<TabPage>())
|
||||
// {
|
||||
// foreach (var descendant in page.CollectChildren<T>(true))
|
||||
// {
|
||||
// yield return descendant;
|
||||
|
||||
// }
|
||||
// }
|
||||
//}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// reference 의 LT 좌표 기준으로, control 의 LT 좌표의 offset 값을 반환한다.
|
||||
/// </summary>
|
||||
/// <param name="control"></param>
|
||||
/// <param name="reference"></param>
|
||||
/// <returns></returns>
|
||||
public static Point GetRelativePoint(this Control control, Control reference)
|
||||
{
|
||||
return reference.PointToClient(control.PointToScreen(control.Location));
|
||||
}
|
||||
|
||||
public static Rectangle GetRelativeRectangle(this Control control, Control reference)
|
||||
{
|
||||
return reference.RectangleToClient(control.RectangleToScreen(control.ClientRectangle));
|
||||
}
|
||||
|
||||
public static void SetBackgroundImage(this Control control, Image image)
|
||||
{
|
||||
if (control.BackgroundImage != null)
|
||||
control.BackgroundImage.Dispose();
|
||||
|
||||
control.BackgroundImage = image;
|
||||
}
|
||||
|
||||
public static void MakeTransparent(this Control control)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (control is Button)
|
||||
((Button) control).FlatStyle = FlatStyle.Flat;
|
||||
|
||||
control.ForceMakeTransparent();
|
||||
control.BackColor = Color.Transparent;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// http://solvedstack.com/questions/transparency-for-windows-forms-textbox
|
||||
/// <c>
|
||||
/// bool itWorked = SetStyle(xControl, ControlStyles.SupportsTransparentBackColor, true);
|
||||
/// </c>
|
||||
/// </summary>
|
||||
/// <param name="control"></param>
|
||||
/// <param name="style"></param>
|
||||
/// <param name="value"></param>
|
||||
/// <returns></returns>
|
||||
public static bool ForceSetStyle(this Control control, ControlStyles style, bool value)
|
||||
{
|
||||
Type typeTB = typeof (Control);
|
||||
System.Reflection.MethodInfo misSetStyle = typeTB.GetMethod("SetStyle",
|
||||
System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance);
|
||||
if (misSetStyle != null && control != null)
|
||||
{
|
||||
misSetStyle.Invoke(control, new object[] {style, value});
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public static bool ForceMakeTransparent(this Control control, bool transparent = true)
|
||||
{
|
||||
return control.ForceSetStyle(ControlStyles.SupportsTransparentBackColor, transparent);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// http://stackoverflow.com/questions/435433/what-is-the-preferred-way-to-find-focused-control-in-winforms-app
|
||||
/// </summary>
|
||||
/// <param name="control"></param>
|
||||
/// <returns></returns>
|
||||
public static Control FindFocusedControl(this Control control)
|
||||
{
|
||||
var container = control as IContainerControl;
|
||||
while (container != null)
|
||||
{
|
||||
control = container.ActiveControl;
|
||||
container = control as IContainerControl;
|
||||
}
|
||||
return control;
|
||||
}
|
||||
|
||||
|
||||
// http://stackoverflow.com/questions/4747935/c-sharp-winform-check-if-control-is-physicaly-visible
|
||||
[DllImport("user32.dll")]
|
||||
static extern IntPtr WindowFromPoint(POINT Point);
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct POINT
|
||||
{
|
||||
public int X;
|
||||
public int Y;
|
||||
|
||||
public POINT(int x, int y) { X = x; Y = y; }
|
||||
public static implicit operator Point(POINT p) => new Point(p.X, p.Y);
|
||||
public static implicit operator POINT(Point p) => new POINT(p.X, p.Y);
|
||||
}
|
||||
|
||||
/// control 이 실제로 사용자에게 보이는지 여부를 반환
|
||||
public static bool IsControlVisibleToUser(this Control control)
|
||||
{
|
||||
return control.DoGet(() =>
|
||||
{
|
||||
if (!control.IsHandleCreated)
|
||||
return false;
|
||||
|
||||
var pos = control.PointToScreen(control.Location);
|
||||
var pointsToCheck = new POINT[] {
|
||||
pos,
|
||||
new Point(pos.X + control.Width - 1, pos.Y),
|
||||
new Point(pos.X, pos.Y + control.Height - 1),
|
||||
new Point(pos.X + control.Width - 1, pos.Y + control.Height - 1),
|
||||
new Point(pos.X + control.Width/2, pos.Y + control.Height/2),
|
||||
};
|
||||
|
||||
foreach (var p in pointsToCheck)
|
||||
{
|
||||
var hwnd = WindowFromPoint(p);
|
||||
var other = Control.FromChildHandle(hwnd);
|
||||
if (other == null)
|
||||
continue;
|
||||
|
||||
if (control == other || control.Contains(other))
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
#region Detect cursor
|
||||
//// http://stackoverflow.com/questions/586479/is-there-a-quick-way-to-get-the-control-thats-under-the-mouse
|
||||
//[DllImport("user32.dll")]
|
||||
//private static extern IntPtr WindowFromPoint(Point pnt);
|
||||
|
||||
//public static Control ControlUnderPoint(this Point pt)
|
||||
//{
|
||||
// IntPtr hWnd = WindowFromPoint(pt);
|
||||
// if (hWnd != IntPtr.Zero)
|
||||
// return Control.FromHandle(hWnd);
|
||||
|
||||
// return null;
|
||||
//}
|
||||
|
||||
//public static Control ControlUnderMouseCursor()
|
||||
//{
|
||||
// return Control.MousePosition.ControlUnderPoint();
|
||||
//}
|
||||
|
||||
/// <summary> Checks whether mouse is over given control </summary>
|
||||
public static bool IsMouseOver(this Control control)
|
||||
{
|
||||
return control.ClientRectangle.Contains(control.PointToClient(Cursor.Position));
|
||||
}
|
||||
|
||||
/// <summary> Collects controls under mouse cursor </summary>
|
||||
public static IEnumerable<Control> GetChildrenUnderMouse(this Control parent)
|
||||
{
|
||||
foreach (var c in parent.Controls.Cast<Control>())
|
||||
{
|
||||
if (c.IsMouseOver())
|
||||
yield return c;
|
||||
foreach (var cc in GetChildrenUnderMouse(c))
|
||||
yield return cc;
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
|
||||
/// Button 에 image 를 입힌다. text 는 왼쪽, image 는 오른쪽
|
||||
public static void AddImage(this Button button, Image image)
|
||||
{
|
||||
button.Image = image;
|
||||
button.ImageAlign = ContentAlignment.MiddleRight;
|
||||
button.TextAlign = ContentAlignment.MiddleLeft;
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user