2092 lines
92 KiB
C#
2092 lines
92 KiB
C#
using System;
|
||
using System.Collections.Generic;
|
||
using System.ComponentModel;
|
||
using System.Drawing;
|
||
using System.Data;
|
||
using System.Text;
|
||
using System.Windows.Forms;
|
||
using System.Drawing.Drawing2D;
|
||
using static System.Windows.Forms.VisualStyles.VisualStyleElement.TaskBand;
|
||
using System.Linq;
|
||
using System.Data.SqlTypes;
|
||
using System.Diagnostics;
|
||
using vmsnet.Attributes;
|
||
using vmsnet.Configures;
|
||
using AR;
|
||
using ScottPlot.TickGenerators.TimeUnits;
|
||
|
||
namespace vmsnet.HMI
|
||
{
|
||
public enum RelayControl
|
||
{
|
||
[Coil(address: 10)]
|
||
mKA
|
||
}
|
||
|
||
public enum ESTATUS
|
||
{
|
||
가동,
|
||
이상,
|
||
대기,
|
||
기타,
|
||
미사용
|
||
}
|
||
|
||
public enum EDRAGTYPE
|
||
{
|
||
GROUP
|
||
}
|
||
|
||
public enum EBUTTONTYPE
|
||
{
|
||
CELL,
|
||
GROUP,
|
||
NBZERO,
|
||
NBRESET,
|
||
PRINT,
|
||
SELGROUP,
|
||
}
|
||
|
||
public partial class DispCtrl : UserControl
|
||
{
|
||
public bool MonitorOn { get; set; }
|
||
public CMouseinfo Mouseinfo; //마우스위치정보
|
||
|
||
//그룹데이터
|
||
public CGROUP[] GROUPS = new CGROUP[0];
|
||
public CWINDOW WINDOW = new CWINDOW();
|
||
|
||
object grplock = new object();
|
||
|
||
public void ResizeGroup(int newsize)
|
||
{
|
||
lock (grplock)
|
||
{
|
||
if (newsize > this.GROUPS.Length)
|
||
{
|
||
Array.Resize(ref GROUPS, newsize);
|
||
}
|
||
}
|
||
}
|
||
public void SetItemDisable()
|
||
{
|
||
lock (grplock)
|
||
{
|
||
foreach (var g in GROUPS)
|
||
{
|
||
foreach (var gi in g.Items)
|
||
{
|
||
gi.활성화 = false;
|
||
gi._onalamh = false;
|
||
gi._onalaml = false;
|
||
gi._onalamover = false;
|
||
gi._p_onalamh = false;
|
||
gi._p_onalaml = false;
|
||
gi._p_onalamover = false;
|
||
gi.mtime = "";
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
public int GroupCount
|
||
{
|
||
get
|
||
{
|
||
if (GROUPS == null) return 0;
|
||
if (GROUPS.Any() == false) return 0;
|
||
return GROUPS.Length;
|
||
}
|
||
}
|
||
public int GroupItemCount
|
||
{
|
||
get
|
||
{
|
||
if (GROUPS == null) return 0;
|
||
if (GROUPS.Any() == false) return 0;
|
||
return GROUPS[0].Items.Length;
|
||
}
|
||
}
|
||
//public void SetGroupItem(CGROUP[] grp)
|
||
//{
|
||
// lock (grplock)
|
||
// {
|
||
// GROUPS = grp;
|
||
// }
|
||
//}
|
||
//public void SetGroupItem(int idx, CGROUP item)
|
||
//{
|
||
// lock (grplock)
|
||
// {
|
||
// GROUPS[idx] = item;
|
||
// }
|
||
//}
|
||
//public CGROUP[] GetGroupItem()
|
||
//{
|
||
// lock (grplock)
|
||
// {
|
||
// return this.GROUPS;
|
||
// }
|
||
//}
|
||
|
||
private int[,,] values;
|
||
private String[,,] times;
|
||
|
||
private Boolean _init = false; //그리드초기화완료여부
|
||
private String _initmsg = "initializing...";
|
||
public int initpercent = 0;
|
||
|
||
//미정리
|
||
public int ZoneMarginX = 0;
|
||
public int ZoneMarginY = 50;
|
||
|
||
public Font Font_Nav = new Font("arial", 9);
|
||
private Font FONT_NANUM_20_BOLD = new Font("나눔고딕", 20, FontStyle.Bold);
|
||
private Font FONT_TAHOMA_80_BOLD = new Font("tahoma", 80, FontStyle.Bold);
|
||
|
||
|
||
/// <summary>
|
||
/// 데이터가 지정된 시간이 넘어가면 이벤트를 이용해서 알림을함(외부의 트렌드뷰에서 사용하려고함)
|
||
/// </summary>
|
||
public int NotifyDataSecond = 2;
|
||
private DateTime LastNotifyTime = DateTime.Now.AddSeconds(-60);
|
||
|
||
//alam1 blick
|
||
private short blink1 = 0;
|
||
private short blink2 = 0;
|
||
private Boolean A1 = false;
|
||
private Boolean A2 = false;
|
||
|
||
public int SmallSize = 300;
|
||
|
||
//140829 데이터분주 추가 (arin)
|
||
public int datadiv = 1;
|
||
|
||
public Font FONT_NB = new Font("Tahoma", 30, FontStyle.Bold);
|
||
public Font FONT_CN = new Font("Tahoma", 8, FontStyle.Bold);
|
||
public Font FONT_CV = new Font("Tahoma", 9, FontStyle.Bold);
|
||
|
||
public Font FONT_CT = new Font("Tahoma", 8, FontStyle.Bold);
|
||
public Font FONT_AV = new Font("Tahoma", 7, FontStyle.Bold);
|
||
|
||
public Font FONT_KA = new Font("Arial", 40, FontStyle.Bold); //ka-value
|
||
public Font FONT_KU = new Font("Arial", 10, FontStyle.Bold); //ka-unit
|
||
public bool EnableKA { get; set; } = false;
|
||
|
||
/// <summary>
|
||
/// 개별보기일때 현재 표시해야할 아이템의 값이 변한경우
|
||
/// </summary>
|
||
public event OnChangedShowIndexHandler OnChangedShowIndex;
|
||
public delegate void OnChangedShowIndexHandler(int index);
|
||
|
||
public event OnNotifyDataHandler OnNotifyData;
|
||
public delegate void OnNotifyDataHandler(DateTime datetCurrenttime);
|
||
|
||
//MY EVENT
|
||
|
||
public event OnClickPrintHandler OnClickPrint; //click print
|
||
public delegate void OnClickPrintHandler(CGROUP idx);
|
||
|
||
public event OnClickProbeSensorHandler OnClickCell; //셀클릭
|
||
public delegate void OnClickProbeSensorHandler(CITEM idx, MouseEventArgs e);
|
||
|
||
public event OnClickGroupHandler OnClickGroup; //그룹클릭
|
||
public delegate void OnClickGroupHandler(CGROUP idx, MouseEventArgs e);
|
||
|
||
public event OnSetNBHandler OnSetNullbalance; //그룹클릭
|
||
public delegate void OnSetNBHandler(CGROUP grp, Single value);
|
||
|
||
public event OnAlamChangeHHandler OnAlamChange; //알람이 변경되었을경우(활성/비활성)
|
||
public delegate void OnAlamChangeHHandler(int ch, COMM.EALAMRAISETYPE raisetype, COMM.EALAMTYPE atype, String AM, Single value, Single maxvalue, Single minvalue);
|
||
|
||
public event OnRaiseAlamChangeHHandler RaiseAlarm; //알람이 변경되었을경우(활성/비활성)
|
||
public delegate void OnRaiseAlamChangeHHandler(Boolean On);
|
||
|
||
public Boolean _raise_alarm = false; //알람발생여부
|
||
public Boolean _raise_alarm_pre = false; //알람발생여부(이전)
|
||
|
||
private short _raise_alarm_count = 0; //셀알람발생카운트(모든그룹의합)
|
||
private short _raise_alarm_nbcount = 0; //셀알람발생카운트(모든그룹의합)
|
||
|
||
private short _pre_raise_alarm_count = 0; //이전알람발생시 만들어진 카운터
|
||
private short _pre_raise_alarm_nbcount = 0; //이전알람발생시 만들어진 널밸런트 카운터
|
||
public Boolean NullbalanceRealValue = true;
|
||
public Boolean Sumab = false; //150320
|
||
|
||
//private CTrendData TrendData = new CTrendData();
|
||
|
||
//화면디자인관련
|
||
private Color bordercolor; //테두리 색상
|
||
private Cursor cursor = Cursors.Default; //현재커서의모양
|
||
private SolidBrush SB_White_200 = new SolidBrush(Color.FromArgb(200, Color.White));
|
||
private SolidBrush SB_WhiteSmoke_200 = new SolidBrush(Color.FromArgb(200, Color.WhiteSmoke));
|
||
private SolidBrush SB_Black_150 = new SolidBrush(Color.FromArgb(200, Color.Black));
|
||
|
||
public Color design_backcolor_start;
|
||
public Color design_backcolor_normal;
|
||
|
||
private string Warn_msg = ""; //경고메세지(화면 최상단중앙에 표시됨)
|
||
private Font Warn_Font;
|
||
|
||
private Font alamfont = new Font("Arial", 8, FontStyle.Bold); //ALAMICON_01
|
||
|
||
//기타설정'
|
||
// public Rectangle[] GroupRect; //그룹머릿글
|
||
// public Rectangle headRect; //머릿부분
|
||
// public Rectangle ItemRect; //아이템표시영역(전체)
|
||
// public Rectangle[] ItemsRect; //세부아이템표시영역(MATRIX 값에따라서 갯수가 변경된다)
|
||
// public Rectangle[] NBRects; //nullbalance Area (그룹갯수별로 잇기때문에 여러개가된다)
|
||
|
||
public RectangleF WindowRect; //윈도우데이터가표시되는 영역
|
||
// public RectangleF BarRect; //바그래프가 표시되는 영역
|
||
// public RectangleF TrendRect; //트렌드뷰가 표시되는 영역
|
||
// public RectangleF NavRect; //네비게이션이 표시되는 영역
|
||
|
||
private Font font_grouptitle = new Font("나눔고딕", 20, FontStyle.Bold);
|
||
private Font font_header = new Font("나눔고딕", 10, FontStyle.Bold);
|
||
|
||
private Color font_grouptitle_color = Color.Red;
|
||
private Color font_header_color = Color.Yellow;
|
||
|
||
//private List<RectangleF> Buttons = new List<RectangleF>(0);
|
||
//private List<Object> Buttonstag = new List<Object>(0);
|
||
//private List<EBUTTONTYPE> Buttonstype = new List<EBUTTONTYPE>(0);
|
||
|
||
private List<CButton> Buttons = new List<CButton>();
|
||
|
||
public Boolean bMakeRect = true;
|
||
|
||
/// <summary>
|
||
/// 개별보기? 전체보기?
|
||
/// </summary>
|
||
private Boolean _FullScreen;
|
||
public Boolean FullScreen
|
||
{
|
||
get
|
||
{
|
||
return _FullScreen;
|
||
}
|
||
set
|
||
{
|
||
_FullScreen = value;
|
||
if (!_FullScreen)
|
||
{
|
||
ShowIndex = 0;
|
||
}
|
||
else ShowIndex = -1;
|
||
}
|
||
}
|
||
|
||
private int _showindex = -1;
|
||
|
||
/// <summary>
|
||
/// 개별보기 모드일때 현재 화면에 표시할 그룹의 인덱스
|
||
/// </summary>
|
||
public int ShowIndex
|
||
{
|
||
get
|
||
{
|
||
return _showindex;
|
||
}
|
||
set
|
||
{
|
||
if (FullScreen)
|
||
{
|
||
//전체홤녀일경우에는 사용하지 않는다.
|
||
_showindex = -1;
|
||
}
|
||
else
|
||
{
|
||
if (value != -1 && value != _showindex)
|
||
{
|
||
_showindex = value;
|
||
if (OnChangedShowIndex != null) OnChangedShowIndex(_showindex);
|
||
}
|
||
}
|
||
|
||
}
|
||
}
|
||
|
||
#region *** Constructors ***
|
||
|
||
public int[,,] Values
|
||
{
|
||
get { return this.values; }
|
||
set { this.values = value; }
|
||
}
|
||
|
||
public String[,,] Times
|
||
{
|
||
get { return this.times; }
|
||
set { this.times = value; }
|
||
}
|
||
public Color Font_Grouptitle_Color
|
||
{
|
||
get { return this.font_grouptitle_color; }
|
||
set { this.font_grouptitle_color = value; }
|
||
}
|
||
|
||
public Color Font_Header_Color
|
||
{
|
||
get { return this.font_header_color; }
|
||
set { this.font_header_color = value; }
|
||
}
|
||
|
||
public Font Font_Grouptitle
|
||
{
|
||
get { return this.font_grouptitle; }
|
||
set { this.font_grouptitle = value; }
|
||
}
|
||
|
||
public Font Font_Header
|
||
{
|
||
get { return this.font_header; }
|
||
set { this.font_header = value; }
|
||
}
|
||
|
||
public DispCtrl()
|
||
{
|
||
InitializeComponent();
|
||
|
||
// Initialize Variables
|
||
|
||
// Set Optimized Double Buffer to reduce flickering
|
||
this.SetStyle(ControlStyles.UserPaint, true);
|
||
this.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
|
||
this.SetStyle(ControlStyles.OptimizedDoubleBuffer, true);
|
||
this.SetStyle(ControlStyles.SupportsTransparentBackColor, true);
|
||
|
||
// Redraw when resized
|
||
this.SetStyle(ControlStyles.ResizeRedraw, true);
|
||
|
||
this.Font = SystemInformation.MenuFont;
|
||
this.Warn_Font = new Font("나눔고딕", 20, FontStyle.Bold);
|
||
|
||
this.Font_Grouptitle = new Font("나눔고딕", 25, FontStyle.Bold);
|
||
this.Font_Header = new Font("나눔고딕", 20, FontStyle.Bold);
|
||
|
||
this.bordercolor = Color.LightGray;
|
||
this.Warn_msg += ("메세지가 없습니다");
|
||
|
||
this.design_backcolor_normal = Color.DarkBlue;
|
||
this.design_backcolor_start = Color.Black;
|
||
this.FullScreen = false;
|
||
}
|
||
|
||
|
||
private void InitializeComponent()
|
||
{
|
||
this.Name = "DispCtrl";
|
||
this.Size = new System.Drawing.Size(287, 321);
|
||
this.Load += new System.EventHandler(this.DispCtrl_Load);
|
||
this.MouseDown += new System.Windows.Forms.MouseEventHandler(this.DispCtrl_MouseDown);
|
||
this.MouseMove += new System.Windows.Forms.MouseEventHandler(this.DispCtrl_MouseMove);
|
||
this.Resize += arLabel_Resize;
|
||
}
|
||
|
||
void arLabel_Resize(object sender, EventArgs e)
|
||
{
|
||
Invalidate();
|
||
}
|
||
|
||
public Boolean init
|
||
{
|
||
get { return this._init; }
|
||
set { this._init = value; }
|
||
}
|
||
private void DispCtrl_Load(object sender, EventArgs e)
|
||
{
|
||
|
||
}
|
||
|
||
#endregion
|
||
|
||
#region *** Properties ***
|
||
|
||
|
||
/// <summary>
|
||
/// 경고메세지를 반환합니다.
|
||
/// </summary>
|
||
public string Message_Warning
|
||
{
|
||
get { return this.Warn_msg.ToString(); }
|
||
set
|
||
{
|
||
if (value == null || string.IsNullOrEmpty(value)) Warn_msg = "";
|
||
else Warn_msg += (value) + "\r\n";
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// 테두리색상
|
||
/// </summary>
|
||
public Color BorderColor
|
||
{
|
||
get { return this.bordercolor; }
|
||
set
|
||
{
|
||
bordercolor = value;
|
||
Update();
|
||
}
|
||
}
|
||
#endregion
|
||
|
||
private RectangleF[] GetRectangleTitle(Graphics g, RectangleF ItemRect, CGROUP grp, Boolean isprint)
|
||
{
|
||
Font applyfont = this.FONT_CT;// grp.셀글꼴;
|
||
if (isprint) applyfont = new Font(applyfont.FontFamily, 6, FontStyle.Bold);
|
||
|
||
String Cellno = grp.maxcellname;
|
||
SizeF CellNoSize = g.MeasureString(Cellno, applyfont);
|
||
SizeF CellAlSize = g.MeasureString("88/88", applyfont);
|
||
|
||
//------------- | ----------- | ------------
|
||
// cell pv alarm
|
||
//------------- | ----------- | ------------
|
||
|
||
Single H = (Single)(CellNoSize.Height * 2.5); //높이값
|
||
Single NameSize = (Single)(CellNoSize.Width * 1.05); //살짝더크게
|
||
Single PvSize = ItemRect.Width - (Single)(CellNoSize.Width * 1.05) - (Single)(CellAlSize.Width);
|
||
Single AlamSize = ItemRect.Width - NameSize - PvSize;
|
||
|
||
RectangleF CellNoRect = new RectangleF(ItemRect.Left, ItemRect.Top, NameSize, H);
|
||
RectangleF CellPvRect = new RectangleF(CellNoRect.Left + CellNoRect.Width, ItemRect.Top, PvSize, H);
|
||
RectangleF CellALRect = new RectangleF(CellPvRect.Left + CellPvRect.Width, ItemRect.Top, AlamSize, H);
|
||
|
||
return new RectangleF[3] { CellNoRect, CellPvRect, CellALRect };
|
||
}
|
||
|
||
private void DrawItem(Graphics g, CGROUP grp, RectangleF R, short CellGroupidx, Boolean isprint, Boolean isVisible)
|
||
{
|
||
RectangleF[] CellTitleRect = DrawCellTitle(g, R, grp, isprint); //0번은 title label ,1 번은 value label
|
||
|
||
grp._cell_title_width = CellTitleRect[0].Width; //셀의 제목표시줄(번호)의 너비값
|
||
grp._cell_value_width = CellTitleRect[1].Width; //셀의 제목표시줄(값)의 너비값
|
||
grp._cell_alam_width = CellTitleRect[2].Width; //셀의 알람표시줄의 너비값
|
||
|
||
Single height = R.Height - CellTitleRect[0].Height; //채널표시영역의 옾이값
|
||
|
||
//실제채널이 표시되는 데이터 표시
|
||
RectangleF channelarea = new RectangleF(R.Left, R.Top + CellTitleRect[0].Height, R.Width, height);
|
||
if (isVisible) DrawCellMatrix(g, channelarea, grp, CellGroupidx, isprint);
|
||
|
||
//vertical line
|
||
Single lx = R.Left + grp._cell_title_width;
|
||
if (isVisible) g.DrawLine(Pens.Silver, lx, R.Top, lx, R.Top + R.Height);
|
||
lx += grp._cell_value_width;
|
||
if (isVisible) g.DrawLine(Pens.Silver, lx, R.Top, lx, R.Top + R.Height);
|
||
if (isVisible) g.DrawLine(Pens.Silver, lx, R.Top + (CellTitleRect[2].Height / 2), lx + grp._cell_alam_width, R.Top + (CellTitleRect[2].Height / 2));
|
||
//lx += grp._cell_alam_width / 2;
|
||
//if (isVisible) g.DrawLine(Pens.Silver, lx, R.Top + (CellTitleRect[2].Height / 2), lx, R.Top + R.Height);
|
||
}
|
||
|
||
private RectangleF[] DrawCellTitle(Graphics g, RectangleF ItemRect, CGROUP grp, Boolean isprint)
|
||
{
|
||
Font applyfont = this.FONT_CT;// grp.셀글꼴;
|
||
if (isprint) applyfont = new Font(applyfont.FontFamily, 6, FontStyle.Bold);
|
||
|
||
String Cellno = grp.maxcellname;
|
||
SizeF CellNoSize = g.MeasureString(Cellno, applyfont);
|
||
SizeF CellAlSize = g.MeasureString("88/88", applyfont);
|
||
|
||
//------------- | ----------- | ------------
|
||
// cell pv alarm
|
||
//------------- | ----------- | ------------
|
||
|
||
Single H = (Single)(CellNoSize.Height * 2.5); //높이값
|
||
Single NameSize = (Single)(CellNoSize.Width * 1.05); //살짝더크게
|
||
Single PvSize = ItemRect.Width - (Single)(CellNoSize.Width * 1.05) - (Single)(CellAlSize.Width);
|
||
Single AlamSize = ItemRect.Width - NameSize - PvSize;
|
||
|
||
RectangleF CellNoRect = new RectangleF(ItemRect.Left, ItemRect.Top, NameSize, H);
|
||
RectangleF CellPvRect = new RectangleF(CellNoRect.Left + CellNoRect.Width, ItemRect.Top, PvSize, H);
|
||
RectangleF CellALRect = new RectangleF(CellPvRect.Left + CellPvRect.Width, ItemRect.Top, AlamSize, H);
|
||
|
||
Color gbclor;
|
||
|
||
if (grp.AlarmType == "AUTO") gbclor = Color.SkyBlue;
|
||
else if (grp.AlarmType == "MANUAL") gbclor = Color.LightGray;
|
||
else gbclor = Color.Pink; //stop
|
||
|
||
|
||
RectangleF TITLERECT = new RectangleF(ItemRect.Left, ItemRect.Top, ItemRect.Width, H - 2);
|
||
g.FillRectangle(new SolidBrush(gbclor), TITLERECT);
|
||
|
||
//DRAW UNDERLINE
|
||
g.DrawLine(Pens.DimGray, TITLERECT.Left, TITLERECT.Top + TITLERECT.Height, TITLERECT.Left + TITLERECT.Width, TITLERECT.Top + TITLERECT.Height);
|
||
//g.DrawRectangle(Pens.Red, TITLERECT.Left, TITLERECT.Top, TITLERECT.Width, TITLERECT.Height);
|
||
|
||
g.DrawString("Cell", applyfont, Brushes.Black, CellNoRect.Left + CellNoRect.Width / 2 - CellNoSize.Width / 2, CellNoRect.Top + CellNoRect.Height / 2 - CellNoSize.Height / 2);
|
||
|
||
Cellno = "PV";
|
||
CellNoSize = g.MeasureString(Cellno, applyfont);
|
||
g.DrawString(Cellno, applyfont, Brushes.Black, CellPvRect.Left + CellPvRect.Width / 2 - CellNoSize.Width / 2, CellPvRect.Top + CellPvRect.Height / 2 - CellNoSize.Height / 2);
|
||
|
||
Cellno = "Alarm";
|
||
CellNoSize = g.MeasureString(Cellno, applyfont);
|
||
|
||
String SH = "H", SL = "L";
|
||
if (grp.AlarmType == "AUTO")
|
||
{
|
||
SH = "+";
|
||
SL = "-";
|
||
}
|
||
|
||
SizeF a, h, l;
|
||
a = g.MeasureString("ALM", applyfont);
|
||
h = g.MeasureString(SH, applyfont);
|
||
l = g.MeasureString(SL, applyfont);
|
||
|
||
//Single y = 0, x = 0;
|
||
g.DrawString("ALM", applyfont, Brushes.Black, CellALRect.Left + CellALRect.Width / 2 - a.Width / 2, CellALRect.Top + CellALRect.Height / 4 - a.Height / 2);
|
||
|
||
|
||
var alrecthl = new RectangleF(CellALRect.X, CellALRect.Y + CellALRect.Height / 2f, CellALRect.Width, CellALRect.Height / 2f);
|
||
g.DrawString($"{SH}/{SL}", applyfont, Brushes.Black, alrecthl, new StringFormat
|
||
{
|
||
LineAlignment = StringAlignment.Center,
|
||
Alignment = StringAlignment.Center
|
||
});
|
||
|
||
|
||
return new RectangleF[3] { CellNoRect, CellPvRect, CellALRect };
|
||
}
|
||
|
||
public String initmsg
|
||
{
|
||
get { return this._initmsg; }
|
||
set
|
||
{
|
||
this._initmsg = value;
|
||
this.Refresh();
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// 화면에 표시되는 내용중 실제 셀의 내용이다. 세부내역은 이곳에서 작성됨
|
||
/// </summary>
|
||
/// <param name="g"></param>
|
||
/// <param name="srcrect"></param>
|
||
/// <param name="grp"></param>
|
||
/// <param name="cidx"></param>
|
||
private void DrawCellMatrix(Graphics g, RectangleF srcrect, CGROUP grp, short cidx, Boolean isprint)
|
||
{
|
||
try
|
||
{
|
||
Single height = (Single)srcrect.Height / grp.RowCount; //지정한 갯수를 나눈다.
|
||
Single newx = srcrect.Left;
|
||
|
||
for (short j = 0; j < grp.RowCount; j++)
|
||
{
|
||
int idx = cidx * grp.RowCount + j;
|
||
Single newy = j * height;
|
||
|
||
RectangleF R =
|
||
new RectangleF(newx + 1, newy + srcrect.Top, grp.Cell_Title_Width + grp.Cell_Value_Width + grp.Cell_Alam_Width - 1, height - 2);
|
||
|
||
//번호와 영역을 재계산한다.
|
||
if (grp.Items.GetUpperBound(0) < idx)
|
||
Array.Resize(ref grp.itemarray, idx + 1);
|
||
|
||
//항목초기화
|
||
if (grp.Items[idx] == null)
|
||
{
|
||
grp.Items[idx] = new CITEM()
|
||
{
|
||
이름 = "--",
|
||
알람형태 = COMM.EALAMTYPE.사용안함,
|
||
alamh = -999,
|
||
alaml = -999,
|
||
aalamh = -999,
|
||
aalaml = -999,
|
||
alamv = -999,
|
||
Onset = false,
|
||
//firstsave = true,
|
||
};
|
||
}
|
||
|
||
CITEM Item = grp.Items[idx];
|
||
|
||
//Single Alamh=0,AlamL=0;
|
||
switch (Item.알람형태)
|
||
{
|
||
case COMM.EALAMTYPE.그룹설정을따름:
|
||
Item.alamh = grp.HIGH;
|
||
Item.alaml = grp.LOW;
|
||
Item.aalamh = grp.UP;
|
||
Item.aalaml = grp.UP;
|
||
//Item.alamv = -999;
|
||
break;
|
||
case COMM.EALAMTYPE.사용안함:
|
||
Item.alamh = -999;
|
||
Item.alaml = -999;
|
||
Item.aalamh = -999;
|
||
Item.aalaml = -999;
|
||
Item.alamv = -999;
|
||
break;
|
||
|
||
case COMM.EALAMTYPE.개별알람자동: //원본값을 그대로 사용한다.
|
||
case COMM.EALAMTYPE.개별알람: //원본값을 그대로 사용한다.
|
||
break;
|
||
}
|
||
|
||
Item.row = j;
|
||
Item.column = cidx;
|
||
Item.rect = R;
|
||
|
||
//기본배경색상(그라디언트)
|
||
Color BackColor = Color.WhiteSmoke;
|
||
var ApplyFont_CN = this.FONT_CN;// grp.셀글꼴;
|
||
var ApplyFont_CV = this.FONT_CV;
|
||
var ApplyFont_AV = this.FONT_AV;
|
||
|
||
if (isprint)
|
||
{
|
||
//출력상태에서는 작게 출력한다.
|
||
ApplyFont_CN = new Font(ApplyFont_CN.FontFamily, 6, FontStyle.Bold);
|
||
ApplyFont_CV = new Font(ApplyFont_CV.FontFamily, 6, FontStyle.Bold);
|
||
ApplyFont_AV = new Font(ApplyFont_AV.FontFamily, 6, FontStyle.Bold);
|
||
}
|
||
|
||
SizeF Fontsize_CN = g.MeasureString(Item.이름, ApplyFont_CN);
|
||
Single fnewx = R.Left + grp.Cell_Title_Width / 2 - Fontsize_CN.Width / 2;
|
||
Single fnewy = R.Top + R.Height / 2 - Fontsize_CN.Height / 2;
|
||
|
||
//알람발생여부초기화
|
||
Item._p_onalamh = Item.onalamh; //이전값기록
|
||
Item._p_onalaml = Item.onalaml; //이전값기록
|
||
Item.onalamh = false; //현재알람초기화
|
||
Item.onalaml = false; //현재알람초기화
|
||
|
||
//데이터표시
|
||
String ValueStr = "";
|
||
Item.CurValue = 0;
|
||
Item.CurValue1 = 0; //140829
|
||
String TimeStr = "";
|
||
|
||
//글자표시색상
|
||
Color BrColor = grp.셀글꼴색상;
|
||
|
||
//값의 저장소가 아에없다면?
|
||
//Boolean OverDATA = false;
|
||
if (this.Values == null)
|
||
{
|
||
Item.value2 = 0;
|
||
Item.CurValue = 0f;
|
||
Item.CurValue1 = 0f;
|
||
TimeStr = "Null Error";
|
||
BrColor = Color.LightGray;
|
||
}
|
||
else
|
||
{
|
||
Single Offset = 0; //수동으로입력된 옾셋
|
||
|
||
if (!Item.사용) //사용여부자체를 설정한다.
|
||
{
|
||
Item.value2 = 0;
|
||
Item.alamv = -999;
|
||
Item.CurValue = 0f; //미설정상태라면 값을 표시하지 않는다.
|
||
Item.CurValue1 = 0f;
|
||
TimeStr = "Not USE";
|
||
grp._unusedcount += 1;
|
||
BackColor = Color.LightGray;
|
||
BrColor = Color.Gray;
|
||
}
|
||
else //정상상태이다.
|
||
{
|
||
//Br = new SolidBrush(Color.Black);
|
||
Offset = Item.Offset; //수동으로입력된 옾셋
|
||
|
||
var u1 = this.Values.GetUpperBound(0);
|
||
var u2 = this.Values.GetUpperBound(1);
|
||
var u3 = this.Values.GetUpperBound(2);
|
||
if (Item.idx_dev >= 0 && Item.idx_unit >= 0 && Item.idx_ch >= 0 &&
|
||
Item.idx_dev <= u1 && Item.idx_unit <= u2 && Item.idx_ch <= u3)
|
||
{
|
||
Item.value2 = this.Values[Item.idx_dev, Item.idx_unit, Item.idx_ch]; //측정값
|
||
TimeStr = this.Times[Item.idx_dev, Item.idx_unit, Item.idx_ch]; //측정시간
|
||
}
|
||
else
|
||
{
|
||
Item.value2 = 0;
|
||
TimeStr = "";
|
||
}
|
||
|
||
if (!Item.활성화) grp._disccount += 1;
|
||
}
|
||
|
||
//backgroun Color
|
||
if (Offset != 0) BrColor = Color.Blue;
|
||
|
||
//OVER DATA
|
||
if (Item.value2 >= 32000 || Item.value2 >= 65000)
|
||
{
|
||
Item._onalamover = true;
|
||
//CurValue = (Single)(Item.value2 / (Math.Pow(10, Item.decpos))) + Offset;
|
||
|
||
//Over aalam
|
||
if (TimeStr != "" && TimeStr != "Not USE" && Item._p_onalamover == false)
|
||
{
|
||
String alamtimes = DateTime.Parse(TimeStr).ToString("yy-MM-dd HH:mm:ss");
|
||
OnAlamChange(Item.idx, COMM.EALAMRAISETYPE.OVER_ON, Item.알람형태, "--", Item.CurValue, Item.alamh, Item.alaml);
|
||
Item._p_onalamover = true;
|
||
}
|
||
Item.CurValue = 0f;
|
||
Item.CurValue1 = 0f;
|
||
}
|
||
else
|
||
{
|
||
Item._onalamover = false;
|
||
|
||
//if(Item.value2 != 9999)
|
||
|
||
//Over aalam
|
||
if (TimeStr != "" && TimeStr != "Not USE" && Item._p_onalamover == true)
|
||
{
|
||
String alamtimes = DateTime.Parse(TimeStr).ToString("yy-MM-dd HH:mm:ss");
|
||
OnAlamChange(Item.idx, COMM.EALAMRAISETYPE.OVER_OFF, Item.알람형태, "--", Item.CurValue, Item.alamh, Item.alaml);
|
||
Item._p_onalamover = false;
|
||
}
|
||
}
|
||
|
||
//현재값
|
||
Item.CurValue = (Single)(Item.value2 / (Math.Pow(10, Item.decpos))) + Offset;
|
||
Item.CurValue1 = Item.CurValue; //데이터분주가 들어있지않은 값이다.
|
||
|
||
//140828 데이터분주값입력
|
||
if (datadiv != 0 && datadiv != 1)
|
||
Item.CurValue = (Single)(Item.CurValue / (Single)datadiv);
|
||
|
||
|
||
//최대,최소,합계VOLT 누적
|
||
if (Item.사용 && Item.활성화)
|
||
{
|
||
//if (Item.CurValue > 0) Debugger.Break();
|
||
|
||
if (Item.CurValue >= grp.Maxvolt)
|
||
{
|
||
grp._maxvolt = Item.CurValue;
|
||
grp._maxitem = Item;
|
||
}
|
||
if (Item.CurValue <= grp.Minvolt)
|
||
{
|
||
grp._minvolt = Item.CurValue;
|
||
grp._minitem = Item;
|
||
}
|
||
grp._sumvolt += Item.CurValue1; //분주되기전의 sum값 140829
|
||
grp._sumvolt1 += Item.CurValue; //분주된후의 sum값 140829
|
||
}
|
||
|
||
//알람활성화여부(오버데이터는 알람설정하지 않는다)
|
||
if (!Item._onalamover && Item.알람형태 != COMM.EALAMTYPE.사용안함 && Item.사용)
|
||
{
|
||
switch (Item.알람형태)
|
||
{
|
||
case COMM.EALAMTYPE.그룹설정을따름:
|
||
if (grp.AlarmType == "AUTO")
|
||
{
|
||
|
||
if (Item.alamv == -999) Item.alamv = Item.CurValue;
|
||
|
||
Item.적용형태 = "AUTO";
|
||
if (Item.CurValue > Item.alamv) //큰값이 있을경우 상한선을 확인한다.
|
||
{
|
||
Single gap = Math.Abs(Item.CurValue - Item.alamv);
|
||
if (gap >= Math.Abs(Item.aalamh))
|
||
{
|
||
Item.onalamh = true;
|
||
Item.onalaml = false;
|
||
BackColor = Color.Orange; //BackColor0 = Color.LightPink;
|
||
}
|
||
}
|
||
else if (Item.CurValue < Item.alamv)
|
||
{
|
||
Single gap = Math.Abs(Item.CurValue - Item.alamv);
|
||
if (gap >= Math.Abs(Item.aalaml))
|
||
{
|
||
Item.onalamh = false;
|
||
Item.onalaml = true;
|
||
BackColor = Color.SkyBlue; //BackColor0 = Color.LightBlue;
|
||
}
|
||
}
|
||
|
||
}
|
||
else if (grp.AlarmType == "MANUAL")
|
||
{
|
||
Item.적용형태 = "MANUAL";
|
||
if (Item.CurValue >= Item.alamh)
|
||
{
|
||
Item.onalamh = true;
|
||
Item.onalaml = false;
|
||
BackColor = Color.Orange;// BackColor0 = Color.LightPink;
|
||
}
|
||
else if (Item.CurValue < Item.alaml)
|
||
{
|
||
Item.onalamh = false;
|
||
Item.onalaml = true;
|
||
BackColor = Color.SkyBlue; //BackColor0 = Color.LightBlue;
|
||
}
|
||
}
|
||
else
|
||
{
|
||
Item.적용형태 = "STOP";
|
||
Item.onalamh = false;
|
||
Item.onalaml = false;
|
||
}
|
||
break;
|
||
case COMM.EALAMTYPE.개별알람:
|
||
Item.적용형태 = "MANUAL";
|
||
if (Item.CurValue >= Item.alamh)
|
||
{
|
||
Item.onalamh = true;
|
||
Item.onalaml = false;
|
||
BackColor = Color.Orange; //BackColor0 = Color.LightPink;
|
||
}
|
||
else if (Item.CurValue < Item.alaml)
|
||
{
|
||
Item.onalamh = false;
|
||
Item.onalaml = true;
|
||
BackColor = Color.SkyBlue;// BackColor0 = Color.LightBlue;
|
||
}
|
||
|
||
break;
|
||
case COMM.EALAMTYPE.개별알람자동:
|
||
Item.적용형태 = "AUTO";
|
||
if (Item.alamv == -999) Item.alamv = Item.CurValue;
|
||
|
||
if (Item.CurValue > Item.alamv) //큰값이 있을경우 상한선을 확인한다.
|
||
{
|
||
Single gap = Math.Abs(Item.CurValue - Item.alamv);
|
||
if (gap >= Math.Abs(Item.aalamh))
|
||
{
|
||
Item.onalamh = true;
|
||
Item.onalaml = false;
|
||
BackColor = Color.Orange; //BackColor0 = Color.LightPink;
|
||
}
|
||
}
|
||
else if (Item.CurValue < Item.alamv)
|
||
{
|
||
Single gap = Math.Abs(Item.CurValue - Item.alamv);
|
||
if (gap >= Math.Abs(Item.aalaml))
|
||
{
|
||
Item.onalamh = false;
|
||
Item.onalaml = true;
|
||
BackColor = Color.SkyBlue; //BackColor0 = Color.LightBlue;
|
||
}
|
||
}
|
||
break;
|
||
}
|
||
}
|
||
//CurValue = (Single)Math.Round(CurValue, 3);
|
||
}
|
||
|
||
|
||
if (Item.활성화 && init == true && (Item.onalaml != Item._p_onalaml || Item._p_onalamh != Item.onalamh)) //이전과 알람상태가 변경된경우다.
|
||
{
|
||
String alamtimes;
|
||
|
||
if (TimeStr != "" && TimeStr != "Not USE") alamtimes = DateTime.Parse(TimeStr).ToString("yy-MM-dd HH:mm:ss");
|
||
else alamtimes = "";
|
||
|
||
Single AH, AL;
|
||
if (Item.적용형태 == "AUTO")
|
||
{
|
||
AH = Item.aalamh;
|
||
AL = Item.aalaml;
|
||
}
|
||
else
|
||
{
|
||
AH = Item.alamh;
|
||
AL = Item.alaml;
|
||
}
|
||
if (Item.onalamh && !Item._p_onalamh)
|
||
{
|
||
|
||
OnAlamChange(Item.idx, COMM.EALAMRAISETYPE.HIGH_ON, Item.알람형태, Item.적용형태, Item.CurValue, AH, AL);
|
||
Item._p_onalamh = true;
|
||
}
|
||
else if (Item.onalaml && !Item._p_onalaml)
|
||
{
|
||
OnAlamChange(Item.idx, COMM.EALAMRAISETYPE.LOW_ON, Item.알람형태, Item.적용형태, Item.CurValue, AH, AL);
|
||
Item._p_onalaml = true;
|
||
}
|
||
else if (!Item.onalamh && Item._p_onalamh)
|
||
{
|
||
OnAlamChange(Item.idx, COMM.EALAMRAISETYPE.HIGH_OFF, Item.알람형태, Item.적용형태, Item.CurValue, AH, AL);
|
||
Item._p_onalamh = false;
|
||
}
|
||
else if (!Item.onalaml && Item._p_onalaml)
|
||
{
|
||
OnAlamChange(Item.idx, COMM.EALAMRAISETYPE.LOW_OFF, Item.알람형태, Item.적용형태, Item.CurValue, AH, AL);
|
||
Item._p_onalamh = false;
|
||
}
|
||
}
|
||
|
||
if (!Item.활성화 && Item.사용)
|
||
{
|
||
Item._onalamover = false;
|
||
Item._onalamh = false;
|
||
Item._onalaml = false;
|
||
Item._p_onalamh = false;
|
||
Item._p_onalaml = false;
|
||
Item._p_onalamover = false;
|
||
|
||
BackColor = Color.WhiteSmoke;
|
||
//BackColor0 = Color.LightGray;
|
||
BrColor = (Color.Gray);
|
||
}
|
||
|
||
if (Item._onalamover)
|
||
{
|
||
ValueStr = $"{Item.CurValue:0.000}";
|
||
BrColor = (Color.DarkMagenta);
|
||
grp._errorcount += 1;
|
||
}
|
||
else if (!Item.활성화)
|
||
{
|
||
ValueStr = "--";
|
||
}
|
||
else ValueStr = $"{Item.CurValue:0.000}";
|
||
|
||
//초기화전상태라면 초기화된걸로 확인시킨다.
|
||
if (!Item.Onset) Item.Onset = true;
|
||
|
||
//Draw Cell Background
|
||
using (var br = new SolidBrush(BackColor))
|
||
g.FillRectangle(br, R);
|
||
|
||
//Border
|
||
using (var pen = new Pen(Color.LightGray))
|
||
{
|
||
g.DrawLine(pen, R.Left + grp.Cell_Title_Width, R.Top, R.Left + grp.Cell_Title_Width, R.Top + R.Height);
|
||
g.DrawLine(pen, R.Left + grp.Cell_Title_Width + grp.Cell_Value_Width, R.Top, R.Left + grp.Cell_Title_Width + grp.Cell_Value_Width, R.Top + R.Height);
|
||
}
|
||
|
||
//Cell 제목줄 표시
|
||
if (Item.사용)
|
||
{
|
||
Color cc;
|
||
if (Item.ismin)
|
||
cc = BrColor = Color.Blue; // <-- Color.DarkBlue;
|
||
else if (Item.ismax)
|
||
cc = BrColor = Color.Red;
|
||
else cc = BrColor;
|
||
|
||
using (var br = new SolidBrush(cc))
|
||
g.DrawString(Item.이름, ApplyFont_CN, br, fnewx, fnewy);
|
||
}
|
||
|
||
Item.Value = ValueStr;
|
||
Item.mtime = TimeStr;
|
||
|
||
|
||
if (idx < grp._null_itemseq)
|
||
{
|
||
if (Item.사용 && Item.활성화)
|
||
{
|
||
grp._sumvoltA += Item.CurValue1;
|
||
if (Item.알람형태 != COMM.EALAMTYPE.사용안함)
|
||
{
|
||
if (NullbalanceRealValue) grp._null_valueL += Item.CurValue1; //알람이 오프된경우라면 처리하지않게한다.
|
||
else grp._null_valueL += Item.CurValue; //알람이 오프된경우라면 처리하지않게한다.
|
||
|
||
}
|
||
}
|
||
}
|
||
else
|
||
{
|
||
if (Item.사용 && Item.활성화)
|
||
{
|
||
grp._sumvoltB += Item.CurValue1;
|
||
if (Item.알람형태 != COMM.EALAMTYPE.사용안함)
|
||
{
|
||
if (NullbalanceRealValue) grp._null_valueR += Item.CurValue1;
|
||
else grp._null_valueR += Item.CurValue;
|
||
}
|
||
}
|
||
}
|
||
|
||
Fontsize_CN = g.MeasureString(ValueStr, ApplyFont_CV);
|
||
fnewx = R.Left + grp.Cell_Title_Width + grp.Cell_Value_Width / 2 - Fontsize_CN.Width / 2;
|
||
fnewy = R.Top + R.Height / 2 - Fontsize_CN.Height / 2;
|
||
|
||
if (this.WINDOW.Debug)
|
||
ValueStr += cidx.ToString();
|
||
|
||
//Cell Value 표시
|
||
if (Item.사용)
|
||
{
|
||
using (var Br = new SolidBrush(BrColor))
|
||
g.DrawString(ValueStr, ApplyFont_CV, Br, fnewx, fnewy);
|
||
}
|
||
|
||
//display alam
|
||
String AlamstrH = "";
|
||
String AlamstrL = "";
|
||
switch (Item.알람형태)
|
||
{
|
||
case COMM.EALAMTYPE.사용안함: //직접사용안함
|
||
BrColor = Color.Gray;
|
||
AlamstrH = "OFF";
|
||
AlamstrL = "OFF";
|
||
break;
|
||
|
||
case COMM.EALAMTYPE.그룹설정을따름:
|
||
BrColor = Color.Black;
|
||
|
||
if (grp.AlarmType == "AUTO")
|
||
{
|
||
AlamstrH = Item.aalamh.ToString();
|
||
AlamstrL = Item.aalaml.ToString();
|
||
}
|
||
else if (grp.AlarmType == "MANUAL")
|
||
{
|
||
AlamstrH = Item.alamh.ToString();
|
||
AlamstrL = Item.alaml.ToString();
|
||
}
|
||
else //그룹설정이 OFF된경우
|
||
{
|
||
AlamstrH = "OFF";
|
||
AlamstrL = "OFF";
|
||
}
|
||
break;
|
||
|
||
case COMM.EALAMTYPE.개별알람:
|
||
BrColor = (Color.Blue);
|
||
AlamstrH = "↑" + Item.alamh.ToString();
|
||
AlamstrL = "↓" + Item.alaml.ToString();
|
||
break;
|
||
|
||
case COMM.EALAMTYPE.개별알람자동:
|
||
BrColor = (Color.Magenta);
|
||
AlamstrH = "+" + Item.aalamh.ToString();
|
||
AlamstrL = "-" + Item.aalaml.ToString();
|
||
break;
|
||
}
|
||
|
||
Fontsize_CN = g.MeasureString(AlamstrH, ApplyFont_AV);
|
||
SizeF fontsize2 = g.MeasureString(AlamstrL, ApplyFont_AV);
|
||
|
||
|
||
fnewy = R.Top + R.Height / 2 - Fontsize_CN.Height / 2;
|
||
|
||
if (Item.사용)
|
||
{
|
||
|
||
if (Item.활성화)
|
||
{
|
||
if (Item._onalamh || Item._onalaml) grp._alamcount += 1;
|
||
|
||
}
|
||
|
||
Color SSBColor = BrColor;
|
||
if (!Item.활성화) SSBColor = Color.Gray;
|
||
|
||
using (var SSB = new SolidBrush(SSBColor))
|
||
{
|
||
fnewx = R.Left + grp.Cell_Title_Width + grp.Cell_Value_Width + (grp.Cell_Alam_Width / 2 - Fontsize_CN.Width) / 2;
|
||
g.DrawString($"{AlamstrH}/{AlamstrL}", ApplyFont_AV, SSB, fnewx, fnewy);
|
||
}
|
||
}
|
||
|
||
//Cell 테두리
|
||
////g.DrawRectangle(new Pen(Color.Gray), R.Left, R.Top, R.Width - 1, R.Height);
|
||
|
||
//Cell Underbar
|
||
g.DrawLine(Pens.Gray, R.Left, (R.Top + R.Height), R.Left + R.Width, (R.Top + R.Height));
|
||
|
||
|
||
//버튼할당을위한 값할당
|
||
this.Buttons.Add(new CButton(R, Item, EBUTTONTYPE.CELL));
|
||
}
|
||
}
|
||
catch (NullReferenceException ex1)
|
||
{
|
||
// 예외 메시지, 파일명, 행 번호를 로그에 기록
|
||
var stackTrace = new System.Diagnostics.StackTrace(ex1, true);
|
||
var frame = stackTrace.GetFrame(0);
|
||
string fileName = frame.GetFileName();
|
||
int lineNumber = frame.GetFileLineNumber();
|
||
|
||
// UI 디스플레이 중, 예외발생 문제
|
||
PUB.log.AddE($"NullReferenceException Message={ex1.Message}, 파일명={fileName}, 행번호={lineNumber}");
|
||
return;
|
||
}
|
||
catch (Exception ex2)
|
||
{
|
||
// 예외 메시지, 파일명, 행 번호를 로그에 기록
|
||
var stackTrace = new System.Diagnostics.StackTrace(ex2, true);
|
||
var frame = stackTrace.GetFrame(0);
|
||
string fileName = frame.GetFileName();
|
||
int lineNumber = frame.GetFileLineNumber();
|
||
|
||
// Else Error !!!
|
||
PUB.log.AddE($"Exception Message={ex2.Message}, 파일명={fileName}, 행번호={lineNumber}");
|
||
return;
|
||
}
|
||
}
|
||
|
||
private void DrawDebugInfo(Graphics g)
|
||
{
|
||
|
||
}
|
||
|
||
public void DrawGroup(Graphics g, CGROUP grp, Point margin, SizeF ItemSize, RectangleF WinRect, int 열번호, int 줄번호, Boolean isprint, bool IsVisible)
|
||
{
|
||
SizeF Fontsize;
|
||
grp._minitem = null;
|
||
grp._maxitem = null;
|
||
|
||
try
|
||
{
|
||
//그룹내의정보를 설정
|
||
Single newx = WinRect.Left + 열번호 * ItemSize.Width;
|
||
Single newy = WinRect.Top + 줄번호 * ItemSize.Height;
|
||
grp.R = new RectangleF(newx + 4, newy + 4, ItemSize.Width * grp.열병합 - 8, ItemSize.Height * grp.줄병합 - 8);
|
||
|
||
//그룹타이틀
|
||
newy = grp.R.Top;
|
||
SizeF FontHeight = g.MeasureString(grp.이름, this.Font_Grouptitle);
|
||
Single newheigth = (FontHeight.Height * 4);
|
||
grp.Rect_Title = new RectangleF(grp.R.Left, newy, grp.R.Width, newheigth);
|
||
newy += newheigth;
|
||
|
||
//전체아이템너비
|
||
newy += 0;
|
||
newheigth = grp.R.Height + grp.R.Top - newy;
|
||
grp.Rect_body = new RectangleF(grp.R.Left, newy, grp.R.Width, newheigth);
|
||
|
||
//각 셀그룹의 영역을 설정함
|
||
Single LastX = 0;
|
||
int Gap = 6;
|
||
grp.CellGroup_Width = (grp.Rect_body.Width / grp.ColumnCount) - ((Gap * (grp.ColumnCount - 1) / grp.ColumnCount));
|
||
grp.CellGroup_Height = grp.Rect_body.Height;
|
||
grp.CellGroup = new RectangleF[grp.ColumnCount];
|
||
for (int ii = 1; ii <= grp.ColumnCount; ii++)
|
||
{
|
||
if (ii == 1)
|
||
{
|
||
//처음개체
|
||
grp.CellGroup[ii - 1] = new RectangleF(grp.Rect_body.Left, grp.Rect_body.Top, grp.CellGroup_Width, grp.CellGroup_Height);
|
||
LastX = grp.CellGroup[ii - 1].Left + grp.CellGroup[ii - 1].Width + Gap;
|
||
}
|
||
else
|
||
{
|
||
//이후개체
|
||
grp.CellGroup[ii - 1] = new RectangleF(LastX, grp.Rect_body.Top, grp.CellGroup_Width, grp.CellGroup_Height);
|
||
LastX += grp.CellGroup_Width + Gap;
|
||
}
|
||
}
|
||
//
|
||
RectangleF GrpRect = new RectangleF(grp.R.Left + margin.X, grp.R.Top + margin.Y, grp.R.Width, grp.R.Height);
|
||
|
||
//그룹제목표시줄(title)
|
||
Single MaxTitleWidth = 0;
|
||
|
||
Color GroupBackColor = Color.DarkMagenta;
|
||
if (this.WINDOW.IDX > 1) GroupBackColor = Color.DarkGreen;
|
||
|
||
RectangleF newbackgrounrect = new RectangleF(grp.Rect_Title.Left + margin.X,
|
||
grp.Rect_Title.Top + margin.Y,
|
||
grp.Rect_Title.Width,
|
||
grp.Rect_Title.Height);
|
||
|
||
if (IsVisible)
|
||
{
|
||
using (var lgb = new LinearGradientBrush(newbackgrounrect, Color.Black, GroupBackColor, LinearGradientMode.BackwardDiagonal))
|
||
g.FillRectangle(lgb, newbackgrounrect);
|
||
}
|
||
|
||
|
||
Fontsize = g.MeasureString(grp.이름, this.font_grouptitle);
|
||
newx = grp.Rect_Title.Left + 10 + margin.X;
|
||
newy = grp.Rect_Title.Top + 7 + margin.Y;// -Fontsize.Height / 2 + grp.Rect_Title.Height / 2;
|
||
//g.DrawString(grp.이름 + this.Buttons.Count.ToString(), this.font_grouptitle, Brushes.Black, newx + 2, newy + 2);
|
||
if (IsVisible)
|
||
g.DrawString(grp.이름, this.font_grouptitle, Brushes.Yellow, newx, newy);
|
||
if (Fontsize.Width > MaxTitleWidth) MaxTitleWidth = Fontsize.Width;
|
||
|
||
//그룹명클릭시에 그룹설정을 오픈하기위해서 버튼을 할당한다.
|
||
RectangleF GrpTITLE = new RectangleF(newx, newy, Fontsize.Width, Fontsize.Height);
|
||
if (IsVisible) this.Buttons.Add(new CButton(GrpTITLE, grp, EBUTTONTYPE.GROUP));
|
||
//this.Buttonstag.Add(grp);
|
||
//this.Buttonstype.Add(EBUTTONTYPE.GROUP);
|
||
|
||
//셀의 갯수를 표시
|
||
newy += Fontsize.Height + 1f;
|
||
int usechcount = grp.Items.Length - grp._unusedcount;
|
||
|
||
String Cellcount = "NO ITEMS";
|
||
Cellcount = (grp.Items.Length - grp._unusedcount).ToString() + " Cell\n" +
|
||
grp._disccount.ToString() + " Disc.\n" +
|
||
(grp._errorcount).ToString() + " Over";
|
||
|
||
|
||
using (Font CellCountfont = new Font(this.font_grouptitle.Name, this.font_grouptitle.Size - 5))
|
||
{
|
||
Fontsize = g.MeasureString(Cellcount, CellCountfont);
|
||
//g.DrawString(Cellcount, CellCountfont, Brushes.Black, newx + 2, newy + 2); //shadow
|
||
if (IsVisible) g.DrawString(Cellcount, CellCountfont, Brushes.Yellow, newx, newy);
|
||
|
||
newy += Fontsize.Height + 1.5f;
|
||
Fontsize = g.MeasureString("Print", CellCountfont);
|
||
|
||
//프린터버튼추가
|
||
RectangleF printbutrect = new RectangleF(newx, newy, (Single)(Fontsize.Width * 1.5), Fontsize.Height);
|
||
if (IsVisible) g.DrawString("Print", CellCountfont, Brushes.White, printbutrect.Left + (printbutrect.Width - Fontsize.Width) / 2, printbutrect.Top + (printbutrect.Height - Fontsize.Height) / 2);
|
||
if (IsVisible) g.DrawRectangle(Pens.White, new Rectangle((int)newx, (int)newy, (int)(Fontsize.Width * 1.5), (int)Fontsize.Height));
|
||
if (IsVisible) Buttons.Add(new CButton(printbutrect, grp, EBUTTONTYPE.PRINT));
|
||
}
|
||
|
||
if (Fontsize.Width > MaxTitleWidth) MaxTitleWidth = Fontsize.Width;
|
||
|
||
//그룹의정보(header)
|
||
Single HeaderWidth = (Single)(grp.Rect_Title.Width - MaxTitleWidth - 20);
|
||
Single HeaderHeigth = (Single)(grp.Rect_Title.Height * 0.8);
|
||
|
||
//헤더정보를 표시
|
||
newx = grp.Rect_Title.Left + margin.X + (grp.Rect_Title.Width - HeaderWidth) - 5;
|
||
newy = grp.Rect_Title.Top + margin.Y + (grp.Rect_Title.Height - HeaderHeigth) / 2;
|
||
|
||
grp.Rect_Header = new RectangleF(newx, newy, HeaderWidth, HeaderHeigth);
|
||
//그림자//g.FillRectangle(new SolidBrush(Color.FromArgb(50,Color.Black)), grp.Rect_Header.Left+2,grp.Rect_Header.Top+2,grp.Rect_Header.Width,grp.Rect_Header.Height);
|
||
if (IsVisible) g.FillRectangle(new SolidBrush(Color.FromArgb(50, Color.Black)), grp.Rect_Header);
|
||
if (IsVisible) g.DrawRectangle(Pens.Black, grp.Rect_Header.Left, grp.Rect_Header.Top, grp.Rect_Header.Width, grp.Rect_Header.Height);
|
||
|
||
//표시영역(body)
|
||
//셀아이템하위 그룹을 표시한다.
|
||
short gidx = 0;
|
||
grp._maxvolt = -999;
|
||
grp._minvolt = 999;
|
||
grp._avgvolt = 0;
|
||
grp._sumvolt = 0;
|
||
grp._sumvolt1 = 0;
|
||
grp._sumvoltA = 0;
|
||
grp._sumvoltB = 0;
|
||
grp._unusedcount = 0; //미사용채널수
|
||
grp._null_valueL = 0;
|
||
grp._null_valueR = 0;
|
||
grp._errorcount = 0;
|
||
grp._disccount = 0;
|
||
grp._alamcount = 0; //알람발생셀수
|
||
grp._alamcountlb = 0;
|
||
|
||
foreach (RectangleF R in grp.CellGroup)
|
||
{
|
||
//해당그룹의 셀을 표시
|
||
DrawItem(g, grp, new RectangleF(R.Left + margin.X, R.Top + margin.Y, R.Width - 1, R.Height), gidx, isprint, IsVisible);
|
||
|
||
//border
|
||
if (IsVisible) g.DrawRectangle(Pens.DarkGray, (int)R.Left + margin.X, (int)R.Top + margin.Y, (int)R.Width - 1, (int)R.Height);
|
||
gidx += 1;
|
||
|
||
//g.DrawString(this.window.disconnecttime.ToString(), this.Font, Brushes.Red, R.Left,R.Top);
|
||
}
|
||
|
||
grp._amp = 0;
|
||
if (grp._ampidx != "" && grp._ampidx != null)
|
||
{
|
||
var buff = grp._ampidx.Split(new char[] { ',' });
|
||
int di1 = int.Parse(buff[0]);
|
||
int di2 = int.Parse(buff[1]);
|
||
int di3 = int.Parse(buff[2]);
|
||
|
||
try
|
||
{
|
||
grp._ampdecpos = 3;
|
||
grp._amp = (float)(this.Values[di1, di2, di3 - 1] / (Math.Pow(10, grp._ampdecpos)));
|
||
}
|
||
catch
|
||
{
|
||
grp._amp = -1f;
|
||
}
|
||
}
|
||
|
||
if (usechcount == 0) grp._avgvolt = 0;
|
||
else grp._avgvolt = grp.Sumvolt1 / usechcount;
|
||
|
||
Single nullvalue = (grp._null_valueR - grp._null_valueL) + grp.NullBalanceOffset;
|
||
String HeaderStr = $"▣ SUM : {grp.Sumvolt:#0.0}";
|
||
if (Sumab)
|
||
{
|
||
HeaderStr += $"\n▣ SUMA : {grp._sumvoltA:#0.000}";
|
||
HeaderStr += $"\n▣ SUMB : {grp._sumvoltB:#0.000}";
|
||
}
|
||
HeaderStr += $"\n▣ AVG : {grp.Avgvolt:#0.000}";
|
||
if (!Sumab)
|
||
{
|
||
HeaderStr += $"\n▣ MAX : {grp.Maxvolt:#0.000}";
|
||
HeaderStr += $"\n▣ MIN : {grp.Minvolt:#0.000}";
|
||
}
|
||
|
||
//집계데이터출력
|
||
Fontsize = g.MeasureString(HeaderStr, this.font_header);
|
||
newy = grp.Rect_Header.Top + 5; // -Fontsize.Height / 2 + grp.Rect_Header.Height / 2;
|
||
if (IsVisible) g.DrawString(HeaderStr, this.font_header, Brushes.White, grp.Rect_Header.Left + 5, newy);
|
||
|
||
//NB데이터와의 SPLITER
|
||
newx = grp.Rect_Header.Left + 5 + Fontsize.Width + 5;
|
||
Single SpliiterY = newy;
|
||
Single SplliterH = newy + grp.Rect_Header.Height - (newy - grp.Rect_Header.Top) * 2;
|
||
if (IsVisible) g.DrawLine(Pens.Black, newx, newy, newx, SplliterH);
|
||
|
||
//NB데이터출력
|
||
newx += 3;
|
||
|
||
//NB용 알람표시
|
||
Single imgwidth = 30;
|
||
Single imgheight = 30;
|
||
if (!(grp.nbh == 0 && grp.nbl == 0))
|
||
{
|
||
if (Math.Abs(nullvalue) > grp.nbl)
|
||
{
|
||
grp._nbalam_l = true; //a2 on
|
||
if (!grp._pre_nbalam_l)
|
||
{
|
||
if (grp.AlarmType != "STOP") OnAlamChange(grp.IDX, COMM.EALAMRAISETYPE.A2_ON, COMM.EALAMTYPE.사용안함, "NB", (Single)nullvalue, (Single)grp.nbl, (Single)grp.nbl);
|
||
grp._pre_nbalam_l = true;
|
||
A2 = false;
|
||
blink2 = 0;
|
||
}
|
||
else //게속발생중이다.
|
||
{
|
||
if (A2 == false)
|
||
{
|
||
if (blink2 >= 1)
|
||
{
|
||
A2 = true;
|
||
blink2 = 0;
|
||
}
|
||
else blink2 += 1;
|
||
}
|
||
else
|
||
{
|
||
if (blink2 >= 1)
|
||
{
|
||
A2 = false;
|
||
blink2 = 0;
|
||
}
|
||
else blink2 += 1;
|
||
}
|
||
}
|
||
}
|
||
else // a2영역보다는 낮으므로 a2를 해제한다.
|
||
{
|
||
grp._nbalam_l = false; //a2 off
|
||
|
||
if (grp._pre_nbalam_l) //이전에 a2알람이 켜져잇엇다면 알람을 끈다.
|
||
{
|
||
OnAlamChange(grp.IDX, COMM.EALAMRAISETYPE.A2_OFF, COMM.EALAMTYPE.사용안함, "NB", (Single)nullvalue, (Single)grp.nbl, (Single)grp.nbl);
|
||
grp._pre_nbalam_l = false;
|
||
blink1 = 0;
|
||
}
|
||
|
||
|
||
if (Math.Abs(nullvalue) > grp.nbh) //a1영역보다 크다면
|
||
{
|
||
grp._nbalam_h = true;
|
||
if (!grp._pre_nbalam_h) //이전에 발생안햇다면
|
||
{
|
||
if (grp.AlarmType != "STOP") OnAlamChange(grp.IDX, COMM.EALAMRAISETYPE.A1_ON, COMM.EALAMTYPE.사용안함, "NB", (Single)nullvalue, (Single)grp.nbh, (Single)grp.nbh);
|
||
grp._pre_nbalam_h = true;
|
||
blink1 = 0;
|
||
}
|
||
else
|
||
{
|
||
if (A1 == false)
|
||
{
|
||
if (blink1 >= 1)
|
||
{
|
||
A1 = true;
|
||
blink1 = 0;
|
||
}
|
||
else blink1 += 1;
|
||
}
|
||
else
|
||
{
|
||
if (blink1 >= 1)
|
||
{
|
||
A1 = false;
|
||
blink1 = 0;
|
||
}
|
||
else blink1 += 1;
|
||
}
|
||
}
|
||
}
|
||
else //둘다적용안되는구역이다.
|
||
{
|
||
grp._nbalam_h = false; //a1 off
|
||
if (grp._pre_nbalam_h) //이전에 a1알람이 켜져잇엇다면 알람을 끈다.
|
||
{
|
||
OnAlamChange(grp.IDX, COMM.EALAMRAISETYPE.A1_OFF, COMM.EALAMTYPE.사용안함, "NB", (Single)nullvalue, (Single)grp.nbl, (Single)grp.nbl);
|
||
grp._pre_nbalam_h = false;
|
||
}
|
||
blink1 = 0;
|
||
blink2 = 0;
|
||
}
|
||
}
|
||
}
|
||
|
||
if (grp.AlarmType == "STOP") //그룹설정이 OFF인경우에는 모두 끈다.
|
||
{
|
||
grp._nbalam_h = false;
|
||
grp._nbalam_l = false;
|
||
}
|
||
|
||
Bitmap B1;
|
||
if (grp._nbalam_h)
|
||
{
|
||
grp._alamcountlb += 1;
|
||
if (A1) B1 = vmsnet.Properties.Resources.Orange_Ball;
|
||
else B1 = vmsnet.Properties.Resources.Red_Ball;
|
||
}
|
||
else B1 = vmsnet.Properties.Resources.Blue_Ball;
|
||
|
||
Bitmap B2;
|
||
if (grp._nbalam_l)
|
||
{
|
||
grp._alamcountlb += 1;
|
||
if (A2) B2 = vmsnet.Properties.Resources.Orange_Ball;
|
||
else B2 = vmsnet.Properties.Resources.Red_Ball;
|
||
}
|
||
else B2 = vmsnet.Properties.Resources.Blue_Ball;
|
||
|
||
if (!isprint || WINDOW.CoulumnCount <= 2)
|
||
{
|
||
if (IsVisible) g.DrawImage(B1, newx + 25 * 0, newy, imgwidth, imgheight);
|
||
Fontsize = g.MeasureString("A1", alamfont);
|
||
if (IsVisible) g.DrawString("A1", alamfont, Brushes.Black, (newx + 25 * 0) + imgwidth / 2 - Fontsize.Width / 2, newy + imgheight / 2 - Fontsize.Height / 2);
|
||
|
||
if (IsVisible) g.DrawImage(B2, newx + 25 * 1, newy, imgwidth, imgheight);
|
||
Fontsize = g.MeasureString("A2", alamfont);
|
||
if (IsVisible) g.DrawString("A2", alamfont, Brushes.Black, (newx + 25 * 1) + imgwidth / 2 - Fontsize.Width / 2, newy + imgheight / 2 - Fontsize.Height / 2);
|
||
|
||
//ADJEST
|
||
if (IsVisible) g.DrawImage(vmsnet.Properties.Resources.Clear_Green_Button, newx + 25 * 0, newy + 2 + imgheight, imgwidth, imgheight);
|
||
if (IsVisible) Buttons.Add(new CButton(new RectangleF(newx + 25 * 0, newy + 2 + imgheight, imgwidth, imgheight), grp, EBUTTONTYPE.NBZERO));
|
||
|
||
//RESET
|
||
if (IsVisible) g.DrawImage(vmsnet.Properties.Resources.Backup_Green_Button, newx + 25 * 1, newy + imgheight, imgwidth, imgheight);
|
||
if (IsVisible) Buttons.Add(new CButton(new RectangleF(newx + 25 * 1, newy + imgheight, imgwidth, imgheight), grp, EBUTTONTYPE.NBRESET));
|
||
}
|
||
|
||
//끝부분에 KA 를 표시한다.
|
||
String Kaunit = grp._ampunit;// +grp._ampidx.ToString() + "/" + grp._ampdecpos.ToString();
|
||
|
||
/* 작성자: 이재웅, 작성일: 2024-12-04, 작성내용: {전류량[KA] × 100} 변경 */
|
||
String MaxKA = (grp._amp * 10f).ToString("#0.00");
|
||
|
||
//Console.WriteLine($"{grp.이름} : {MaxKA} {grp._ampunit}");
|
||
|
||
Fontsize = g.MeasureString(MaxKA, FONT_KA);
|
||
SizeF FontSizeu = g.MeasureString(Kaunit, FONT_KU);
|
||
RectangleF KARECT = new RectangleF(grp.Rect_Header.Left + grp.Rect_Header.Width - Fontsize.Width, grp.Rect_Header.Top + (grp.Rect_Header.Height - Fontsize.Height), Fontsize.Width, Fontsize.Height);
|
||
if (EnableKA == false)
|
||
KARECT = new RectangleF(grp.Rect_Header.Right, KARECT.Top, 0, 0);
|
||
//g.FillRectangle(Brushes.Black, KARECT);
|
||
if (IsVisible && KARECT.IsEmpty == false)
|
||
{
|
||
g.DrawString(MaxKA.ToString(), FONT_KA, Brushes.Black, KARECT.Left + 2, KARECT.Top + 2);
|
||
g.DrawString(MaxKA.ToString(), FONT_KA, Brushes.Yellow, KARECT.Left, KARECT.Top);
|
||
g.DrawString(Kaunit, FONT_KU, Brushes.Yellow, KARECT.Left + KARECT.Width - FontSizeu.Width - 10, KARECT.Top - 10);
|
||
}
|
||
|
||
//NullBalance Display
|
||
if (!isprint || WINDOW.CoulumnCount <= 2)
|
||
{
|
||
newx = newx + 30 * 2;
|
||
String nullstring = nullvalue.ToString("#0.00");
|
||
RectangleF rect_nullb = new RectangleF(newx, newy, KARECT.Left - newx, grp.Rect_Header.Height - 10);
|
||
Fontsize = g.MeasureString(nullstring, FONT_NB);
|
||
Single center = rect_nullb.Left + rect_nullb.Width / 2;
|
||
Single px = ((rect_nullb.Width / 2) * Math.Abs(nullvalue) / 5);
|
||
if (nullvalue < -5)
|
||
{
|
||
px = (rect_nullb.Width * (0) / (5 + 5)) - 1;
|
||
}
|
||
else if (nullvalue > 5)
|
||
{
|
||
px = (rect_nullb.Width * (5 + 5) / (5 + 5)) - 1;
|
||
}
|
||
else px = (rect_nullb.Width * (nullvalue + 5) / (5 + 5)) - 1;
|
||
|
||
Color nbcolor = Color.White;
|
||
if (grp._nbalam_h) nbcolor = Color.Orange;
|
||
else if (grp._nbalam_l) nbcolor = Color.Red;
|
||
else nbcolor = Color.White;
|
||
|
||
if (IsVisible) g.DrawString(nullstring, FONT_NB, new SolidBrush(Color.FromArgb(230, nbcolor)), newx + rect_nullb.Width / 2 - Fontsize.Width / 2, rect_nullb.Top + rect_nullb.Height / 2 - Fontsize.Height / 2);
|
||
|
||
|
||
Color NewSBColor;
|
||
if (grp.NullBalanceOffset != 0) NewSBColor = Color.FromArgb(180, Color.DarkBlue);
|
||
else NewSBColor = Color.FromArgb(180, Color.Red);
|
||
using (SolidBrush NewSB = new SolidBrush(NewSBColor))
|
||
{
|
||
if (IsVisible) g.DrawLine(Pens.Red, px + rect_nullb.Left, rect_nullb.Top, px + rect_nullb.Left, rect_nullb.Top + rect_nullb.Height);
|
||
if (IsVisible) g.DrawLine(Pens.Red, px + rect_nullb.Left + 1, rect_nullb.Top, px + rect_nullb.Left + 1, rect_nullb.Top + rect_nullb.Height);
|
||
PointF[] sqp = new PointF[3];
|
||
sqp[0] = new PointF(px + rect_nullb.Left - 10, rect_nullb.Top);
|
||
sqp[1] = new PointF(px + rect_nullb.Left, rect_nullb.Top + 10);
|
||
sqp[2] = new PointF(px + rect_nullb.Left + 10, rect_nullb.Top);
|
||
if (IsVisible) g.FillPolygon(Brushes.Red, sqp);
|
||
NewSB.Dispose();
|
||
}
|
||
|
||
//null balance 테두리 그림
|
||
if (IsVisible) g.DrawRectangle(Pens.Orange, rect_nullb.Left, rect_nullb.Top, rect_nullb.Width, rect_nullb.Height);
|
||
var term = rect_nullb.Width / 10f;
|
||
for (int i = 1; i < 10; i++)
|
||
{
|
||
var x = rect_nullb.Left + (i * term);
|
||
var y = (rect_nullb.Top + (rect_nullb.Height * 0.8f));
|
||
var y2 = rect_nullb.Top + rect_nullb.Height;
|
||
|
||
if (IsVisible) g.DrawLine(Pens.Orange, x - 1, y, x - 1, y2);
|
||
//String str = (i - 5).ToString();
|
||
}
|
||
|
||
newx = newx + rect_nullb.Width + 3;
|
||
if (IsVisible) g.DrawLine(Pens.Black, newx, SpliiterY, newx, SplliterH);
|
||
}
|
||
else
|
||
{
|
||
if (IsVisible)
|
||
{
|
||
String nullstring = "NB=" + nullvalue.ToString("#0.00");
|
||
using (var nullbfont = new Font(FONT_NB.FontFamily, 10))
|
||
{
|
||
g.DrawString(nullstring, nullbfont, SB_White_200, KARECT.Left, KARECT.Top - 10);
|
||
}
|
||
}
|
||
}
|
||
|
||
//현그룹의 테두리 그림
|
||
//g.DrawRectangle(Pens.Black, (int)grp.R.Left, (int)grp.R.Top, (int)grp.R.Width+1, (int)grp.R.Height);
|
||
//grp.Showinfo = true;
|
||
|
||
//추가헤더정보
|
||
if (!isprint && grp.Showinfo && IsVisible)
|
||
{
|
||
using (var ifont = new Font(this.font_header, FontStyle.Bold))
|
||
{
|
||
String nbstr = $"▣ {grp.이름} - NULL BALANCE ▣";
|
||
nbstr += "\n\n▶L:" + grp._null_valueL.ToString("#0.00") + "v";
|
||
nbstr += ",R:" + grp._null_valueR.ToString("#0.00") + "v";
|
||
nbstr += " ▶DEV(R-L):" + (grp._null_valueR - grp._null_valueL).ToString("#0.00") + "v";
|
||
nbstr += " ▶Adj. Offset:" + (grp.NullBalanceOffset).ToString("#0.00") + "v";
|
||
nbstr += "\n\n▶Null Balance : " + (grp._null_valueR - grp._null_valueL + grp.NullBalanceOffset).ToString("#0.00") + "v";
|
||
nbstr += "\n▶Null Balance Alarm: A1(" + grp.nbh.ToString("#0.00") + "),A2(" + grp.nbl.ToString("#0.00") + ")";
|
||
nbstr += "\n\n * 막대그래프의 구간은 -5v ~ 5v 입니다.";
|
||
nbstr += "\n * 막대그래프의 색상이 하늘색일경우에는 Adj.Offset 이 적용된 값입니다.";
|
||
|
||
SizeF fs = g.MeasureString(nbstr, ifont);
|
||
Single tx, ty, tw, th, Margin = 0;
|
||
|
||
tx = grp.Rect_Header.Left + 10;
|
||
ty = grp.Rect_Header.Top + grp.Rect_Header.Height - 6;
|
||
tw = (fs.Width * 1.1f);
|
||
th = (fs.Height * 1.1f + 60);
|
||
|
||
RectangleF infoboxb = new RectangleF(tx + 1, ty + 1, tw, th);
|
||
RectangleF infoboxf = new RectangleF(tx, ty, tw, th);
|
||
RectangleF intoboxs = new RectangleF(tx + Margin + 3, ty + Margin, tw - (Margin * 2), th - (Margin * 2));
|
||
|
||
//SolidBrush BRB = new SolidBrush(Color.FromArgb(150, Color.Black));
|
||
//SolidBrush BRF = new SolidBrush(Color.FromArgb(200, Color.White));
|
||
|
||
g.FillRectangle(SB_Black_150, infoboxb);
|
||
g.FillRectangle(SB_White_200, infoboxf);
|
||
|
||
g.DrawString(nbstr, ifont, Brushes.Black, intoboxs.Left + 1, intoboxs.Top + 3);
|
||
// g.DrawString(nbstr, this.font_header, Brushes.Orange, intoboxs.Left, intoboxs.Top + intoboxs.Height / 2 - fs.Height / 2);
|
||
|
||
Single Imagey = intoboxs.Top + fs.Height + 10;
|
||
|
||
g.DrawImage(vmsnet.Properties.Resources.Clear_Green_Button, intoboxs.Left, Imagey, imgwidth, imgheight);
|
||
g.DrawString("현재 Null Balance 값을 Adj.Offset 으로 설정하여 '0'이 되게 합니다.", ifont, Brushes.Black, intoboxs.Left + 35, Imagey + 5);
|
||
|
||
Imagey += 25;
|
||
g.DrawImage(vmsnet.Properties.Resources.Backup_Green_Button, intoboxs.Left, Imagey, imgwidth, imgheight);
|
||
g.DrawString("입력된 Adj.Offset 을 제거하여 원래의 Null Balance가 보이게 합니다.", ifont, Brushes.Black, intoboxs.Left + 35, Imagey + 5);
|
||
|
||
//BRF.Dispose();
|
||
}
|
||
}
|
||
|
||
_raise_alarm_count += grp._alamcount;
|
||
_raise_alarm_nbcount += grp._alamcountlb;
|
||
|
||
if (grp._maxitemp != null)
|
||
{
|
||
grp._maxitemp.ismax = false;
|
||
}
|
||
if (grp._minitemp != null) grp._minitemp.ismin = false;
|
||
if (grp._maxitem != null)
|
||
{
|
||
grp._maxitem.ismax = true;
|
||
grp._maxitemp = grp._maxitem;
|
||
}
|
||
if (grp._minitem != null)
|
||
{
|
||
grp._minitem.ismin = true;
|
||
grp._minitemp = grp._minitem;
|
||
}
|
||
}
|
||
catch (NullReferenceException ex1)
|
||
{
|
||
// 예외 메시지, 파일명, 행 번호를 로그에 기록
|
||
var stackTrace = new System.Diagnostics.StackTrace(ex1, true);
|
||
var frame = stackTrace.GetFrame(0);
|
||
string fileName = frame.GetFileName();
|
||
int lineNumber = frame.GetFileLineNumber();
|
||
|
||
// UI 디스플레이 중, 예외발생 문제
|
||
PUB.log.AddE($"NullReferenceException Message={ex1.Message}, 파일명={fileName}, 행번호={lineNumber}");
|
||
return;
|
||
}
|
||
catch (Exception ex2)
|
||
{
|
||
// 예외 메시지, 파일명, 행 번호를 로그에 기록
|
||
var stackTrace = new System.Diagnostics.StackTrace(ex2, true);
|
||
var frame = stackTrace.GetFrame(0);
|
||
string fileName = frame.GetFileName();
|
||
int lineNumber = frame.GetFileLineNumber();
|
||
|
||
// Else Error !!!
|
||
PUB.log.AddE($"Exception Message={ex2.Message}, 파일명={fileName}, 행번호={lineNumber}");
|
||
return;
|
||
}
|
||
}
|
||
|
||
private void DrawGroups(Graphics g)
|
||
{
|
||
_raise_alarm_count = 0; //알람카운트
|
||
_raise_alarm_nbcount = 0;
|
||
|
||
|
||
//윈도우크기를 설정해준다(개체의크기와 같다)
|
||
if (!FullScreen)
|
||
{
|
||
//개별표시면모드 150313
|
||
//현재화면에 1개의 그룹만 표시한다.
|
||
this.WINDOW._itemwidth = this.WindowRect.Width; // / this.window.CoulumnCount;
|
||
this.WINDOW._itemheight = WindowRect.Height; // / this.window.RowCount;
|
||
}
|
||
else
|
||
{
|
||
//전체화면 모드이므로 지정된 갯수만큼 사이즈를 조절한다.
|
||
this.WINDOW._itemwidth = WindowRect.Width / this.WINDOW.CoulumnCount;
|
||
this.WINDOW._itemheight = WindowRect.Height / this.WINDOW.RowCount;
|
||
}
|
||
|
||
|
||
if (this.GROUPS.Length < 1)
|
||
{
|
||
g.DrawString("NO Group", this.Font, Brushes.Red, WindowRect.Left, WindowRect.Top);
|
||
}
|
||
else
|
||
{
|
||
//150313
|
||
//if (FullScreen)
|
||
//{
|
||
var idx = 0;
|
||
CGROUP infogrp = null;
|
||
//if (GROUPS[0].이름 == "EL2500E") Debugger.Break();
|
||
foreach (CGROUP grp in this.GROUPS)
|
||
{
|
||
var visible = true;
|
||
var 열번호 = grp.열번호;
|
||
var 줄번호 = grp.줄번호;
|
||
|
||
//전체화면이 아닌경우라면 지정된 그룹만 표시한다
|
||
if (FullScreen == false)
|
||
{
|
||
if (ShowIndex < 0 || ShowIndex > this.GROUPS.GetUpperBound(0)) visible = false; //인덱스오류체크
|
||
else visible = (idx == ShowIndex);
|
||
열번호 = 0;
|
||
줄번호 = 0;
|
||
}
|
||
|
||
|
||
|
||
//마우스를 올린경우 추가정보 표시
|
||
if (grp.Showinfo) infogrp = grp;
|
||
//else
|
||
//{
|
||
DrawGroup(g, grp, new Point(0, 0), new SizeF(WINDOW.ITEMWIDTH, WINDOW.ITEMHEIGHT), WindowRect, 열번호, 줄번호, false, visible);
|
||
//}
|
||
|
||
idx += 1;
|
||
}
|
||
|
||
if (infogrp != null)
|
||
{
|
||
var colnum = infogrp.열번호;
|
||
var rownum = infogrp.줄번호;
|
||
if (FullScreen == false)
|
||
{
|
||
colnum = 0;
|
||
rownum = 0;
|
||
}
|
||
DrawGroup(g, infogrp, new Point(0, 0), new SizeF(WINDOW.ITEMWIDTH, WINDOW.ITEMHEIGHT), WindowRect, colnum, rownum, false, true);
|
||
|
||
}
|
||
|
||
//end group
|
||
//}
|
||
//else
|
||
//{
|
||
// //개별표시모드이므로 지정된 index 그룹만 표시한다.
|
||
// if (ShowIndex < 0 || ShowIndex > this.GROUPS.GetUpperBound(0))
|
||
// {
|
||
// //인덱스값이 잘못된경우이므로 처리할 수 없다
|
||
// g.DrawString("개별그룹보기 인덱스 오류 index=" + ShowIndex.ToString(), this.Font, Brushes.Red, 100, 200);
|
||
// }
|
||
// else
|
||
// {
|
||
// CGROUP grp = this.GROUPS[ShowIndex];
|
||
// DrawGroup(g, grp, new Point(0, 0), new SizeF(WINDOW.ITEMWIDTH, WINDOW.ITEMHEIGHT), WindowRect, 0, 0, false);
|
||
// }
|
||
|
||
//}
|
||
}
|
||
|
||
|
||
if (_raise_alarm_count > 0 || _raise_alarm_nbcount > 0) _raise_alarm = true; //현재알람이 켜져야한다.
|
||
else _raise_alarm = false;
|
||
|
||
//g.DrawString(_raise_alarm_count.ToString(), this.font_grouptitle, Brushes.White, 100, 100);
|
||
//g.DrawString(_raise_alarm_nbcount.ToString(), this.font_grouptitle, Brushes.White, 100, 200);
|
||
|
||
//알람의강제오프기능이 활성화되었다면?
|
||
//현재 알람이 활성화되어있다면 알람을 해제한다.
|
||
//이전알람과비교해서 달라졌다면 알람을 발생시켜준다.
|
||
//단 상태가 같은데 현재 알람카운터가 이전알람카운터보다 클경우에는 알람을 다시 발생한다.
|
||
|
||
if (_raise_alarm && !_raise_alarm_pre) { RaiseAlarm(true); _raise_alarm_pre = true; } //이전에는 발생안했다가 새로 발생한경우
|
||
if (!_raise_alarm && _raise_alarm_pre) { RaiseAlarm(false); _raise_alarm_pre = false; } //이전에 발생했다가 끄는경우
|
||
if ((_raise_alarm_count > _pre_raise_alarm_count || _pre_raise_alarm_nbcount > _raise_alarm_nbcount) && _raise_alarm) //알람이켜져잇는상태에서 알람카운터가 증가했다면 재 알람
|
||
{
|
||
RaiseAlarm(true);
|
||
_raise_alarm_pre = true;
|
||
}
|
||
|
||
_pre_raise_alarm_count = _raise_alarm_count;
|
||
_pre_raise_alarm_nbcount = _raise_alarm_nbcount;
|
||
|
||
}
|
||
|
||
|
||
|
||
/// Override OnPaint method
|
||
protected override void OnPaint(PaintEventArgs e)
|
||
{
|
||
base.OnPaint(e);
|
||
this.SuspendLayout();
|
||
|
||
try
|
||
{
|
||
///각영역을 새로 만들어야하는경우이다.
|
||
if (bMakeRect)
|
||
{
|
||
if (FullScreen)
|
||
{
|
||
WindowRect = new RectangleF(Padding.Left, Padding.Top, this.Width - Padding.Left - Padding.Right, this.Height - Padding.Top - Padding.Bottom);
|
||
//TrendRect = new RectangleF(0,0,0,0);
|
||
// BarRect = new RectangleF(0, 0, 0, 0);
|
||
// NavRect = new RectangleF(0, 0, 0, 0);
|
||
}
|
||
else
|
||
{
|
||
|
||
WindowRect = new RectangleF(Padding.Left, Padding.Top, this.Width - Padding.Left - Padding.Right, this.Height - Padding.Top - Padding.Bottom);
|
||
|
||
//개별화면일경우
|
||
// int WindowWidth = SmallSize; // (int)((this.Width - Padding.Left - Padding.Right) * 0.4);
|
||
// int halfHeight = (int)((this.Height- Padding.Top - Padding.Bottom - 50-10) * 0.5);
|
||
// WindowRect = new RectangleF(Padding.Left, Padding.Top, WindowWidth, this.Height - Padding.Top - Padding.Bottom);
|
||
|
||
// NavRect = new RectangleF(WindowRect.Right + 10, WindowRect.Top, this.Width - WindowRect.Right - 10 - 1, 50);
|
||
// TrendRect = new RectangleF(NavRect.Left, WindowRect.Top + 50, this.Width - WindowRect.Right - 10 - 1, halfHeight);
|
||
// BarRect = new RectangleF(NavRect.Left, TrendRect.Bottom + 10, TrendRect.Width, halfHeight);
|
||
}
|
||
bMakeRect = false;
|
||
}
|
||
|
||
Buttons = new List<CButton>(0);
|
||
//Buttonstag = new List<Object>(0);
|
||
//Buttonstype = new List<EBUTTONTYPE>(0);
|
||
|
||
Boolean isnull = false;
|
||
if (!init) isnull = true;
|
||
else
|
||
{
|
||
if (this.WINDOW == null || this.GROUPS == null) isnull = true;
|
||
if (isnull && this.GROUPS.Length == 0) isnull = true;
|
||
}
|
||
|
||
//표시아이템이없다면 오류를 낸다.
|
||
if (isnull)
|
||
{
|
||
//progress
|
||
int bw = (int)(this.Width * 0.8);
|
||
int bh = 30;
|
||
|
||
Rectangle rr = new Rectangle((this.Width - bw) / 2, (this.Height - bh) / 2, bw, bh);
|
||
Rectangle FullRect = new Rectangle(0, 0, this.Width, this.Height);
|
||
using (var gradientBrush = new LinearGradientBrush(FullRect, Color.White, Color.White, LinearGradientMode.Vertical))
|
||
{
|
||
e.Graphics.FillRectangle(gradientBrush, FullRect);
|
||
SizeF initsize = e.Graphics.MeasureString(initmsg, FONT_NANUM_20_BOLD);
|
||
e.Graphics.DrawString(initmsg, FONT_NANUM_20_BOLD, Brushes.Black, this.Width / 2 - initsize.Width / 2, this.Height / 2 - initsize.Height / 2 - bh - 20);
|
||
}
|
||
|
||
using (var lb = new LinearGradientBrush(rr, Color.LightBlue, Color.SkyBlue, LinearGradientMode.Vertical))
|
||
{
|
||
if (initpercent > 100) initpercent = 100;
|
||
int perc = (int)(rr.Width * initpercent / 100);
|
||
e.Graphics.FillRectangle(lb, new Rectangle(rr.Left, rr.Top, perc, rr.Height));
|
||
e.Graphics.DrawRectangle(Pens.DarkGray, rr);
|
||
e.Graphics.DrawRectangle(Pens.DarkGoldenrod, FullRect.Left, FullRect.Top, FullRect.Width - 1, FullRect.Height - 1);
|
||
}
|
||
|
||
this.ResumeLayout();
|
||
return;
|
||
}
|
||
|
||
// AntiAliasing
|
||
e.Graphics.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.AntiAlias;
|
||
|
||
//그룹목록
|
||
DrawGroups(e.Graphics); /* GROUPS 화면 Display !!! */
|
||
|
||
//monitor off display
|
||
if (MonitorOn == false)
|
||
{
|
||
e.Graphics.FillRectangle(SB_WhiteSmoke_200, DisplayRectangle);
|
||
e.Graphics.DrawString("MONITOR PAUSE", FONT_TAHOMA_80_BOLD, Brushes.Gray, DisplayRectangle, new StringFormat
|
||
{
|
||
Alignment = StringAlignment.Center,
|
||
LineAlignment = StringAlignment.Center,
|
||
});
|
||
}
|
||
|
||
//if (!FullScreen && ShowIndex >= 0)
|
||
{
|
||
//트렌드뷰용채널데이터를 새로 만드는경우
|
||
//if (bMakeTrendViewChData) MakeTrendViewChData();
|
||
|
||
//마지막데이터와 2초의 차이가 있다면 데이터를 생성해준다.
|
||
DateTime NOwdate = DateTime.Now;
|
||
TimeSpan ts = NOwdate - LastNotifyTime;
|
||
if (ts.TotalSeconds >= NotifyDataSecond)
|
||
{
|
||
//알림
|
||
if (OnNotifyData != null) OnNotifyData(NOwdate);
|
||
LastNotifyTime = NOwdate;
|
||
}
|
||
}
|
||
}
|
||
catch (NullReferenceException ex1)
|
||
{
|
||
// 예외 메시지, 파일명, 행 번호를 로그에 기록
|
||
var stackTrace = new System.Diagnostics.StackTrace(ex1, true);
|
||
var frame = stackTrace.GetFrame(0);
|
||
string fileName = frame.GetFileName();
|
||
int lineNumber = frame.GetFileLineNumber();
|
||
|
||
// UI 디스플레이 중, 예외발생 문제
|
||
PUB.log.AddE($"NullReferenceException Message={ex1.Message}, 파일명={fileName}, 행번호={lineNumber}");
|
||
return;
|
||
}
|
||
catch (Exception ex2)
|
||
{
|
||
// 예외 메시지, 파일명, 행 번호를 로그에 기록
|
||
var stackTrace = new System.Diagnostics.StackTrace(ex2, true);
|
||
var frame = stackTrace.GetFrame(0);
|
||
string fileName = frame.GetFileName();
|
||
int lineNumber = frame.GetFileLineNumber();
|
||
|
||
// Else Error !!!
|
||
PUB.log.AddE($"Exception Message={ex2.Message}, 파일명={fileName}, 행번호={lineNumber}");
|
||
return;
|
||
}
|
||
}
|
||
|
||
|
||
protected override void OnResize(EventArgs e)
|
||
{
|
||
base.OnResize(e);
|
||
bMakeRect = true;
|
||
//bMakeBarRect = true;
|
||
Invalidate();
|
||
}
|
||
|
||
private int Check_GroupHeader(MouseEventArgs e, Boolean resetshowinfo = false)
|
||
{
|
||
if (this.GROUPS == null) return -1;
|
||
|
||
|
||
|
||
for (int i = 0; i < this.GROUPS.Length; i++)
|
||
{
|
||
RectangleF rect = this.GROUPS[i].Rect_Header;
|
||
if (resetshowinfo) this.GROUPS[i].Showinfo = false;
|
||
|
||
//현재위치가 해당 Rectagle 안이라면 속해있다.
|
||
if (e.X > rect.X && e.X < rect.X + rect.Width)
|
||
{
|
||
if (e.Y > rect.Y && e.Y < rect.Y + rect.Height)
|
||
{
|
||
//전체화면이 아닌경우에는 선택된 그룹번호를 반환
|
||
if (this.FullScreen == false)
|
||
{
|
||
if (this.ShowIndex < 0 || this.ShowIndex >= this.GroupCount) return -1;
|
||
else return this.ShowIndex;
|
||
}
|
||
else return i;
|
||
}
|
||
}
|
||
}
|
||
return -1;
|
||
}
|
||
|
||
private int Check_Group(MouseEventArgs e)
|
||
{
|
||
if (this.GROUPS == null) return -1;
|
||
for (int i = 0; i < this.GROUPS.Length; i++)
|
||
{
|
||
RectangleF rect = this.GROUPS[i].R;
|
||
|
||
//현재위치가 해당 Rectagle 안이라면 속해있다.
|
||
if (e.X > rect.X && e.X < rect.X + rect.Width)
|
||
{
|
||
if (e.Y > rect.Y && e.Y < rect.Y + rect.Height) return i;
|
||
}
|
||
}
|
||
return -1;
|
||
}
|
||
|
||
private int check_buttons(MouseEventArgs e)
|
||
{
|
||
if (this.Buttons == null) return -1;
|
||
for (int i = 0; i < this.Buttons.Count; i++)
|
||
{
|
||
RectangleF rect = this.Buttons[i].Rect;
|
||
|
||
//현재위치가 해당 Rectagle 안이라면 속해있다.
|
||
if (e.X > rect.X && e.X < rect.X + rect.Width)
|
||
{
|
||
if (e.Y > rect.Y && e.Y < rect.Y + rect.Height) return i;
|
||
}
|
||
}
|
||
return -1;
|
||
}
|
||
|
||
|
||
private void DispCtrl_MouseDown(object sender, MouseEventArgs e)
|
||
{
|
||
//현재마우스위치의 아이템을 찾ㄴ은다.
|
||
int idx = check_buttons(e);
|
||
if (idx != -1)
|
||
{
|
||
CButton But = Buttons[idx];
|
||
//Object tt = this.Buttonstag[idx];
|
||
//EBUTTONTYPE BT = this.Buttonstype[idx];
|
||
|
||
switch (But.ButtonType)
|
||
{
|
||
case EBUTTONTYPE.SELGROUP:
|
||
ShowIndex = ((CGROUP)But.Tag).IDX - 1;
|
||
//bMakeTrendViewChData = true;
|
||
//bMakeBarRect = true;
|
||
// MakeTrendViewChData();
|
||
break;
|
||
case EBUTTONTYPE.CELL:
|
||
OnClickCell((CITEM)But.Tag, e);
|
||
break;
|
||
case EBUTTONTYPE.GROUP:
|
||
OnClickGroup((CGROUP)But.Tag, e);
|
||
break;
|
||
case EBUTTONTYPE.NBRESET:
|
||
//MessageBox.Show("NBRESET" + idx.ToString() );
|
||
((CGROUP)But.Tag).NullBalanceOffset = 0;
|
||
this.OnSetNullbalance((CGROUP)(But.Tag), 0f);
|
||
this.Refresh();
|
||
break;
|
||
case EBUTTONTYPE.NBZERO:
|
||
//MessageBox.Show("NBZERO" + idx.ToString());
|
||
Single Offset = ((CGROUP)But.Tag)._null_valueR - ((CGROUP)But.Tag)._null_valueL;
|
||
((CGROUP)But.Tag).NullBalanceOffset = -1 * Offset;
|
||
this.OnSetNullbalance((CGROUP)(But.Tag), (Single)(-1 * Offset));
|
||
this.Refresh();
|
||
break;
|
||
|
||
case EBUTTONTYPE.PRINT:
|
||
OnClickPrint(((CGROUP)But.Tag));
|
||
break;
|
||
|
||
|
||
}
|
||
}
|
||
}
|
||
|
||
private void DispCtrl_MouseMove(object sender, MouseEventArgs e)
|
||
{
|
||
//마우스위치를 저장한다.
|
||
if (this.Mouseinfo == null) this.Mouseinfo = new CMouseinfo(new PointF(e.X - WindowRect.Left, e.Y - WindowRect.Top));
|
||
else this.Mouseinfo.Position = new PointF(e.X - WindowRect.Left, e.Y - WindowRect.Top);
|
||
|
||
//스피드체크영역이라면 마우스를 핸드로 변경한다.
|
||
Mouseinfo.Hand = false;
|
||
Mouseinfo.Cross = false;
|
||
Mouseinfo.Move = false;
|
||
|
||
//이동중인데 마우스가 눌려있다면 DRAG다
|
||
if (e.Button == MouseButtons.Left) Mouseinfo.Drag = true;
|
||
else Mouseinfo.Drag = false;
|
||
|
||
if (Mouseinfo.Drag) //드래그중이다
|
||
{
|
||
if (Mouseinfo.DragType != EDRAGTYPE.GROUP) Mouseinfo.Move = true; //화면이동으로
|
||
else Mouseinfo.Hand = true; //잡은형태
|
||
}
|
||
|
||
if (this.FullScreen)
|
||
{ /* 작성자: 이재웅, 작성일: 2024-12-04, 작성내용: '전체보기' 상태일 때만 그룹헤더의 [Null Balance] 팝업 정보가 표시되도록 변경 */
|
||
|
||
//마우스가 현재 그룹헤더에 존재하는지확인 (헤더에 올경우 특정 정보를 표시)
|
||
if (!Mouseinfo.Hand && !Mouseinfo.Move)
|
||
{
|
||
int tpidx = Check_GroupHeader(e, true);
|
||
if (tpidx != -1)
|
||
{
|
||
Mouseinfo.Hand = true;
|
||
this.GROUPS[tpidx].Showinfo = true;
|
||
//this.showHeaderInfo = true;
|
||
}
|
||
|
||
}
|
||
//마우스가 현재 그룹에 존재하는지?
|
||
if (!Mouseinfo.Hand && !Mouseinfo.Move)
|
||
{
|
||
int tpidx = Check_Group(e);
|
||
if (tpidx != -1)
|
||
{
|
||
Mouseinfo.Hand = true;
|
||
}
|
||
}
|
||
}
|
||
|
||
if (Mouseinfo.Hand) this.Cursor = Cursors.Hand;
|
||
if (Mouseinfo.Cross) this.Cursor = Cursors.Cross;
|
||
|
||
this.Refresh();
|
||
}
|
||
|
||
|
||
|
||
} //end class
|
||
|
||
} //end namespace |