QuakeGod
2024-12-24 61deef5cdf96cbfdd6ad45be49e80d597c00ca65
提交 | 用户 | age
0ed438 1 
418cb3 2 // MultiTerminal2View.cpp: CMTerm1View 类的实现
0ed438 3 //
Q 4
5 #include "pch.h"
6 #include "framework.h"
7 // SHARED_HANDLERS 可以在实现预览、缩略图和搜索筛选器句柄的
8 // ATL 项目中进行定义,并允许与该项目共享文档代码。
9 #ifndef SHARED_HANDLERS
10 #include "MTerm1.h"
11 #endif
12
13 #include "MTerm1Doc.h"
14 #include "MTerm1View.h"
418cb3 15 #include "ChildFrm.h"
Q 16 #include "DialogSetCoil.h"
17 #include "DialogSetData.h"
18 #include "DialogIoComment.h"
19 #include "KDefine.h"
df0321 20 #include "MainFrm.h"
0ed438 21
Q 22 #ifdef _DEBUG
23 #define new DEBUG_NEW
24 #endif
25
26
27 // CMTerm1View
28
418cb3 29 IMPLEMENT_DYNCREATE(CMTerm1View, CScrollView)
0ed438 30
d34256 31 /// <summary>
Z 32 /// 消息映射
33 /// 是 MFC 中用于将 Windows 消息(如鼠标点击、按键等)映射到成员函数的机制。
34 /// </summary>
418cb3 35 BEGIN_MESSAGE_MAP(CMTerm1View, CScrollView)
0ed438 36     // 标准打印命令
418cb3 37     ON_COMMAND(ID_FILE_PRINT, &CScrollView::OnFilePrint)
Q 38     ON_COMMAND(ID_FILE_PRINT_DIRECT, &CScrollView::OnFilePrint)
39     ON_COMMAND(ID_FILE_PRINT_PREVIEW, &CScrollView::OnFilePrintPreview)
40
41     ON_WM_CREATE()
42     ON_WM_TIMER()
43     ON_WM_ERASEBKGND()
44     ON_WM_SIZE()
45
46     ON_WM_LBUTTONDOWN()
47     ON_WM_LBUTTONUP()
48     ON_WM_LBUTTONDBLCLK()
49     ON_WM_RBUTTONDOWN()
0ed438 50     ON_WM_RBUTTONUP()
418cb3 51     ON_WM_CONTEXTMENU()
Q 52     ON_WM_INITMENUPOPUP()
53
54     ON_COMMAND(ID_RECT_SELECT, &CMTerm1View::OnRectSelect)
55     ON_UPDATE_COMMAND_UI(ID_RECT_SELECT, &CMTerm1View::OnUpdateRectSelect)
56     ON_COMMAND(ID_TEXT_FIRST, &CMTerm1View::OnTextFirst)
57     ON_UPDATE_COMMAND_UI(ID_TEXT_FIRST, &CMTerm1View::OnUpdateTextFirst)
58     ON_COMMAND(ID_INSERT_BLANK_LINE, &CMTerm1View::OnInsertBlankLine)
59     ON_UPDATE_COMMAND_UI(ID_INSERT_BLANK_LINE, &CMTerm1View::OnUpdateInsertBlankLine)
60     ON_COMMAND(ID_DELETE_BLANK_LINE, &CMTerm1View::OnDeleteBlankLine)
61     ON_UPDATE_COMMAND_UI(ID_DELETE_BLANK_LINE, &CMTerm1View::OnUpdateDeleteBlankLine)
62     ON_COMMAND(ID_DISPLAY_COMMENTS, &CMTerm1View::OnDisplayComments)
63     ON_UPDATE_COMMAND_UI(ID_DISPLAY_COMMENTS, &CMTerm1View::OnUpdateDisplayComments)
64     ON_COMMAND(ID_MONITOR, &CMTerm1View::OnMonitor)
65     ON_UPDATE_COMMAND_UI(ID_MONITOR, &CMTerm1View::OnUpdateMonitor)
66     ON_COMMAND(ID_PROG_CONVERT, &CMTerm1View::OnProgConvert)
67     ON_UPDATE_COMMAND_UI(ID_PROG_CONVERT, &CMTerm1View::OnUpdateProgConvert)
68     ON_COMMAND(ID_PROG_CANCEL_EDIT, &CMTerm1View::OnProgCancelEdit)
69     ON_UPDATE_COMMAND_UI(ID_PROG_CANCEL_EDIT, &CMTerm1View::OnUpdateProgCancelEdit)
70     ON_COMMAND(ID_INPUT_IO_COMMENT, &CMTerm1View::OnInputIoComment)
71
72
73     //    ON_UPDATE_COMMAND_UI_RANGE(ID_INDICATOR_MACHINE_TYPE, ID_INDICATOR_INFO_DISPLAY, OnUpdateIndicators)
74     ON_COMMAND_RANGE(ID_INDICATOR_MACHINE_TYPE, ID_INDICATOR_INFO_DISPLAY, NULL)
75 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_MACHINE_TYPE, &CMTerm1View::OnUpdateMachineType)
76 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_PROGRAM_POS, &CMTerm1View::OnUpdateProgramPos)
77 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_CONNECTIVITY, &CMTerm1View::OnUpdateConnectivity)
78 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_RUN_STATUS, &CMTerm1View::OnUpdateRunStatus)
79 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_MONITOR_STATUS, &CMTerm1View::OnUpdateMonitorStatus)
80 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_TARGET_ADDRESS, &CMTerm1View::OnUpdateTargetAddress)
81 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_INFO_DISPLAY, &CMTerm1View::OnUpdateDisplayComments)
82
83 //    ON_COMMAND(ID_INDICATOR_MONITOR_STATUS, &CMTerm1View::OnIndicatorMonitorStatus)
84 //    ON_UPDATE_COMMAND_UI(ID_INDICATOR_MONITOR_STATUS, &CMTerm1View::OnUpdateIndicatorMonitorStatus)
61deef 85     ON_WM_KEYDOWN()
0ed438 86 END_MESSAGE_MAP()
418cb3 87
0ed438 88
Q 89 // CMTerm1View 构造/析构
90
91 CMTerm1View::CMTerm1View() noexcept
92 {
93     // TODO: 在此处添加构造代码
94
95 }
96
97 CMTerm1View::~CMTerm1View()
98 {
99 }
100
101 BOOL CMTerm1View::PreCreateWindow(CREATESTRUCT& cs)
102 {
103     // TODO: 在此处通过修改
104     //  CREATESTRUCT cs 来修改窗口类或样式
105
418cb3 106     return CScrollView::PreCreateWindow(cs);
Q 107 }
108
d34256 109 /// <summary>
Z 110 ///  MFC 中的一个函数,它在视图首次显示之前被调用
111 /// </summary>
418cb3 112 void CMTerm1View::OnInitialUpdate()
Q 113 {
114     CScrollView::OnInitialUpdate();
d34256 115
Z 116     //创建了三种不同的字体
418cb3 117     TextFont.CreateFont(13, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_ROMAN, _T("宋体"));
Q 118     MonTextFont.CreateFont(12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_ROMAN, _T("宋体"));
119     AnnoFont.CreateFont(12, 0, 0, 0, FW_NORMAL, FALSE, FALSE, 0, ANSI_CHARSET, OUT_DEFAULT_PRECIS, CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY, DEFAULT_PITCH | FF_ROMAN, _T("宋体"));
d34256 120     
Z 121     //获取了状态栏的引用并存储在 m_pStatusBar 成员变量中
418cb3 122     m_pStatusBar = ((CChildFrame *)GetParentFrame())->GetStatusBar();
d34256 123
418cb3 124     CSize sizeTotal;
Q 125     // TODO: 计算此视图的合计大小
126     sizeTotal.cx = m_LeftMargin + m_CellWidth* m_CellPerLine + m_CellWidth *2;
127     sizeTotal.cy = 2000;
d34256 128     //设置了滚动大小
418cb3 129     SetScrollSizes(MM_TEXT, sizeTotal);
d34256 130
Z 131     CString s1;//没啥用
132
133     //设置了两个定时器,一个间隔为50毫秒,另一个为10毫秒。
418cb3 134     SetTimer(1, 50,NULL);
Q 135     SetTimer(2, 10, NULL);
136
0ed438 137 }
Q 138
139 // CMTerm1View 绘图
140
418cb3 141 void CMTerm1View::OnDraw(CDC* pDC)
0ed438 142 {
Q 143     CMTerm1Doc* pDoc = GetDocument();
144     ASSERT_VALID(pDoc);
145     if (!pDoc)
146         return;
147
148     // TODO: 在此处为本机数据添加绘制代码
d34256 149     CString s1;//没啥用
Z 150
418cb3 151     needReDraw = 1;
Q 152     DrawLDSGraph(pDC);
153     needReDraw = 0;
0ed438 154 }
Q 155
d34256 156 // CMTerm1View 打印,MFC 函数,用于准备打印。
0ed438 157 BOOL CMTerm1View::OnPreparePrinting(CPrintInfo* pInfo)
Q 158 {
159     // 默认准备
160     return DoPreparePrinting(pInfo);
161 }
162
d34256 163 // MFC 函数,用于在打印开始之前进行初始化。
0ed438 164 void CMTerm1View::OnBeginPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)
Q 165 {
166     // TODO: 添加额外的打印前进行的初始化过程
167 }
168
d34256 169 //MFC 函数,用于在打印结束后进行清理。
0ed438 170 void CMTerm1View::OnEndPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/)
Q 171 {
172     // TODO: 添加打印后进行的清理过程
173 }
174
175
176 // CMTerm1View 诊断
177
178 #ifdef _DEBUG
d34256 179 //函数用于验证对象的有效性。
0ed438 180 void CMTerm1View::AssertValid() const
Q 181 {
418cb3 182     CScrollView::AssertValid();
d34256 183  }
0ed438 184
d34256 185 // 函数用于将对象的内容转储到指定的上下文。
0ed438 186 void CMTerm1View::Dump(CDumpContext& dc) const
Q 187 {
418cb3 188     CScrollView::Dump(dc);
0ed438 189 }
Q 190
d34256 191 //函数返回与此视图关联的文档对象。
0ed438 192 CMTerm1Doc* CMTerm1View::GetDocument() const // 非调试版本是内联的
Q 193 {
194     ASSERT(m_pDocument->IsKindOf(RUNTIME_CLASS(CMTerm1Doc)));
195     return (CMTerm1Doc*)m_pDocument;
196 }
197 #endif //_DEBUG
198
d34256 199 //MFC 函数,用于处理视图的创建事件。
418cb3 200 int CMTerm1View::OnCreate(LPCREATESTRUCT lpCreateStruct)
Q 201 {
202     if (CScrollView::OnCreate(lpCreateStruct) == -1)
203         return -1;
204
205     // TODO:  在此添加您专用的创建代码
206
207     return 0;
208 }
209
d34256 210 /// <summary>
Z 211 /// 用于重新绘制视图。
212 /// </summary>
213 /// <returns></returns>
418cb3 214 int CMTerm1View::DoReDraw()
Q 215 {
d34256 216
418cb3 217     CPoint scroll1;
Q 218     scroll1 = this->GetScrollPosition();
219
220     CClientDC dc1(this);
221     XFORM xform1;
222     xform1.eM11 = 1;
223     xform1.eM12 = 0;
224     xform1.eM21 = 0;
225     xform1.eM22 = 1;
226     xform1.eDx = float(-scroll1.x);
227     xform1.eDy = float(-scroll1.y);
228
229     XFORM xform2 = { 1, 0, 0, 1, 0, 0 };
230
231     dc1.SetGraphicsMode(GM_ADVANCED);
232     dc1.SetWorldTransform(&xform1);
233
234     DrawLDSGraph(&dc1);
235     
236     return 0;
237 }
238
d34256 239 /// <summary>
Z 240 /// 滚动到特定单元格
241 /// 函数内部计算了单元格的总高度,考虑了是否显示注释
242 /// </summary>
243 /// <param name="nRow"></param>
244 /// <param name="nCol"></param>
245 /// <returns></returns>
418cb3 246 int CMTerm1View::ScrollToCell(int nRow, int nCol)
Q 247 {
248     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
249
250     CSize sizeTotal;
251     // TODO: 计算此视图的合计大小
252     sizeTotal.cx = m_LeftMargin + m_CellWidth * m_CellPerLine + m_CellWidth * 2;
253     sizeTotal.cy = m_TopMargin + CellTotalHeight * (m_nTotalRow );
254     CSize sizeSb;
255     GetScrollBarSizes(sizeSb);
256     POINT pt1;
257     pt1.x = 0;
258     pt1.y = nRow * CellTotalHeight;
259     ScrollToPosition(pt1);
260     return 0;
261 }
262
d34256 263 /// <summary>
Z 264 /// 滚动单元格进入视图(未完成的功能)
265 /// </summary>
266 /// <param name="nRow"></param>
267 /// <param name="nCol"></param>
268 /// <returns></returns>
418cb3 269 int CMTerm1View::ScrollCellIntoView(int nRow, int nCol)
Q 270 {
271     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
272     return 0;
273 }
274
d34256 275 /// <summary>
Z 276 /// 检查单元格是否在视图中(未完成的功能)
277 /// </summary>
278 /// <param name="nRow"></param>
279 /// <param name="nCol"></param>
280 /// <returns></returns>
418cb3 281 int CMTerm1View::isCellInView(int nRow, int nCol)
Q 282 {
283     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
284     return 0;
285 }
286
d34256 287 /// <summary>
Z 288 /// 用于在视图中绘制图形的主要函数
289 /// </summary>
290 /// <param name="pDC">文档</param>
291 /// <returns></returns>
418cb3 292 int CMTerm1View::DrawLDSGraph(CDC* pDC)
Q 293 {
294     // TODO: 在此处添加实现代码.
d34256 295     CString s1;//没啥用
Z 296
297     //验证文档引用
418cb3 298     CMTerm1Doc* pDoc = GetDocument();
Q 299     ASSERT_VALID(pDoc);
300     if (!pDoc)    return false;
d34256 301
418cb3 302     if (m_bMonitoring) {
Q 303         pDoc->DoPLCMonitor();
304     }
d34256 305
418cb3 306     int x1, y1, x2, y2;
Q 307     //    RECT rect1;
308     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
309
310     int nDataType, nDataAddr;
311     int nStat;
d34256 312     CBrush br0(BkColor);//背景颜色
Z 313     CBrush br01(BkEditColor);//编辑(选中)状态下的背景颜色
418cb3 314     int nRow, nCol;
Q 315     CRect rect0;
316     this->GetClientRect(&rect0);
317     int viewWidth = rect0.Width();
318     CPoint scroll1;
319     scroll1 = this->GetScrollPosition();
320
d34256 321     int nFirstVisibleLine;//用于确定可见行范围-起始位置
Z 322     int nLastVisibleLine;//用于确定可见行范围-终止位置
323     //通过滚动位置和视图的高度计算上述两个值
418cb3 324     nFirstVisibleLine = (scroll1.y - m_TopMargin) / CellTotalHeight;
Q 325     nLastVisibleLine = (rect0.Height() + scroll1.y - m_TopMargin) / CellTotalHeight + 1;
d34256 326     if (nFirstVisibleLine < 0) 
Z 327     {
328         nFirstVisibleLine = 0; 
329     }
330     if (nLastVisibleLine < 0)
331     { 
332         nLastVisibleLine = 0; 
333     }
418cb3 334
d34256 335     //选择字体
418cb3 336     CFont *pOldFont;
Q 337     pOldFont = (CFont *)pDC->SelectObject(&TextFont);
338
d34256 339     for (int i = nFirstVisibleLine; i < nLastVisibleLine && i < 1000; i++) 
Z 340     {
418cb3 341         // 画一行 单元
Q 342         nRow = i;
343         int x0, y0;
344         x0 = m_LeftMargin;
345         y0 = m_TopMargin + CellTotalHeight * i;
346         y2 = y0 + CellTotalHeight;
347         //画背景
348         if (needReDraw) {
349             // 左半部分
350             if (scroll1.x < x0) {
351                 CRect rect1(scroll1.x, y0, x0, y2);
352                 pDC->FillRect(&rect1, &br0);
353             }
354             //中间部分
355             x1 = max(scroll1.x, x0);
356             x2 = min(scroll1.x + viewWidth, x0 + m_CellPerLine * m_CellWidth);
357             CRect rect2(x1, y0, x2, y2);
358             //背景颜色
359             if (!Cells[nRow][0].bEditing){
360                 pDC->FillRect(&rect2, &br0);
361             }    else {
362                 pDC->FillRect(&rect2, &br01);
363             }
364             // 右边部分
365             if (x2 < scroll1.x + viewWidth)    {
366                 CRect rect3(x2, y0, scroll1.x + viewWidth, y2);
367                 pDC->FillRect(&rect3, &br0);
368             }
369
370             if (m_FocusRow == i)     DrawFocusRect(pDC);
371
372         }
373         //*
374         // 画本行左侧母线
375         x1 = m_LeftMargin;
376         y1 = m_TopMargin + CellTotalHeight * i;
377         x2 = x1;
378         y2 = y1 + CellTotalHeight;
379
380         pDC->MoveTo(x1, y1);
381         pDC->LineTo(x2, y2);
382         //画左侧母线小短横线
383
384
385         x1 = m_LeftMargin;
386         y1 = m_TopMargin + CellTotalHeight * i + m_LinePosY;
387         x2 = x1 + 3;
388         y2 = y1;
389         pDC->MoveTo(x1, y1);
390         pDC->LineTo(x2, y2);
391
392         // 如果本行第一个ST是程序段的起始,输出程序步数
393         //*/
394         int nType = Cells[nRow][0].nType;
395         int nProgSetp = Cells[nRow][0].nProgStep;
396         if (nType == typeNO || nType == typeNC || nType == typeCMP) {
397             int nPairTo = pDoc->Progs[nProgSetp].PairTo;
398             int nPairOp = 0;
399             if (nPairTo) nPairOp = pDoc->Progs[nPairTo].nOpType1;
400             if (nPairOp == 0) { //程序段开始
401                 //在当前行的左侧输出 当前 程序步数
402                 s1.Format(_T("  %d"), nProgSetp);
403                 CRect rect2(0, m_TopMargin + CellTotalHeight * i + m_LinePosY - 8, m_LeftMargin - 4, m_TopMargin + CellTotalHeight * i + m_LinePosY + 14);
404                 pDC->DrawText(s1, &rect2, DT_RIGHT);
405
406             }
407         }
408         // 获取数据  并显示各单元
df0321 409
418cb3 410         for (int j = 0; j < m_CellPerLine; j++) {
Q 411             nCol = j;
412             nDataType = Cells[nRow][nCol].nDataType;
413             nDataAddr = Cells[nRow][nCol].nDataAddr;
df0321 414             if (m_bMonitoring) {
Q 415                 if ((nDataType & TYPEDATA) == TYPEDATA) {
416                     nStat = pDoc->GetVarData(nDataType, nDataAddr);
417                 }
418                 else {
419                     nStat = pDoc->GetCoilValue(nDataType, nDataAddr);
420                 }
421                 Cells[nRow][nCol].nStat = nStat;
422                 nType = Cells[nRow][nCol].nType;
423                 if (nType == typeNO || nType == typeNC || nType == typeCMP || nType == typeTM)
424                 {
425                     int nProgStep = Cells[nRow][nCol].nProgStep;
426                     int nBinProgStep = pDoc->Progs[nProgStep].nBinStep;
427                     Cells[nRow][nCol].nTrace = pDoc->ProgTrace[nBinProgStep];
428                 }
418cb3 429             }
Q 430             else {
df0321 431                 Cells[nRow][nCol].nStat = 0; Cells[nRow][nCol].nTrace = 0;
418cb3 432             }
df0321 433
418cb3 434             DrawCell(pDC, i, j);
Q 435         }
436
437
438         // 画本行右侧母线
439 //*
440         x1 = m_LeftMargin + m_CellWidth * m_CellPerLine;
441         y1 = m_TopMargin + CellTotalHeight * i;
442         x2 = x1;
443         y2 = y1 + CellTotalHeight;
444
445         pDC->MoveTo(x1, y1);
446         pDC->LineTo(x2, y2);
447         // 画本行右侧母线小短横线
448         x1 = m_LeftMargin + m_CellWidth * m_CellPerLine;
449         y1 = m_TopMargin + CellTotalHeight * i + m_LinePosY;
450         x2 = x1 - 3;
451         y2 = y1;
452         pDC->MoveTo(x1, y1);
453         pDC->LineTo(x2, y2);
454
455         //*/
456     }
457     pDC->SelectObject(pOldFont);
458     CRect rect2(0, 30, 240, 100);
459     //    pDC->DrawText(_T("这是测试字符串111,222,33,aa,bb,cc"), &rect2, 0);
460     s1.Format(_T("This is New Info.."));
461     needReDraw = 0;
462     return 0;
463 }
464
465 void  CMTerm1View::DrawFocusRect(CDC* pDC)
466 {
467 //    DrawCell(pDC, m_oldFocusRow, m_oldFocusCol);
468     CPen BluePen(PS_SOLID, 3, FocusColor);
469     CPen * pOldPen = pDC->SelectObject(&BluePen);
470     //CBrush * pOldBrush = ;
471     pDC->SelectStockObject(NULL_BRUSH);
472     int x0, y0;
473     //    int x1, y1, x2, y2;
474     RECT rect1;
475     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
476
477     rect1.left = m_LeftMargin + 1 + m_CellWidth * m_FocusCol;
478     rect1.right = rect1.left + m_CellWidth - 4;
479     rect1.top = m_TopMargin + CellTotalHeight * m_FocusRow;
480     rect1.bottom = rect1.top + CellTotalHeight - 2;
481
482     x0 = rect1.left;
483     y0 = rect1.top;
484     //pDC->DrawFocusRect(&rect1);
485     pDC->Rectangle(&rect1);
486     m_oldFocusCol = m_FocusCol;
487     m_oldFocusRow = m_FocusRow;
488
489     pDC->SelectObject(pOldPen);
490 //    pDC->SelectObject(poldBrush);
491 }
492
493 int CMTerm1View::DrawLeftRightLine(CDC* pDC, int x0, int y0, int size1, int size2)
494 {
495     // TODO: 在此处添加实现代码.
496     int x1, y1, x2, y2;
497     //画左侧横线
498     x1 = x0;
499     y1 = y0 + m_LinePosY;
500     x2 = x1 + size1;
501     y2 = y1;
502     pDC->MoveTo(x1, y1);
503     pDC->LineTo(x2, y2);
504
505     //画右侧横线
506     x1 = x0 + size1 +size2;
507     y1 = y0 + m_LinePosY;
508     x2 = x0 + m_CellWidth;
509     y2 = y1;
510     pDC->MoveTo(x1, y1);
511     pDC->LineTo(x2, y2);
512     return 0;
513 }
514
515 void CMTerm1View::DrawOT(CDC* pDC, int x0, int y0)
516 {
517     int x1, y1;
518     //画左右侧横线
519     DrawLeftRightLine(pDC, x0, y0);
520
521     x1 = x0 +16;
522     y1 = y0 + m_LinePosY;
523
524     pDC->MoveTo(x1 + 6 + 6, y1);
525     pDC->AngleArc(x1 + 6, y1, 6, 0, 360);
526 }
527
528 void  CMTerm1View::DrawRelay(CDC* pDC, int x0, int y0)
529 {
530     int x1, y1, x2, y2;
531     //画左右侧横线
532     DrawLeftRightLine(pDC, x0, y0);
533     // 画左侧竖线
534     x1 = x0+16;
535     y1 = y0 + m_LinePosY - 6;
536     x2 = x1;
537     y2 = y1 + 12;
538     pDC->MoveTo(x1, y1);
539     pDC->LineTo(x2, y2);
540     // 画右侧竖线
541     x1 = x2 + 12;
542     y1 = y1;
543     x2 = x1;
544     y2 = y1 + 12;
545     pDC->MoveTo(x1, y1);
546     pDC->LineTo(x2, y2);
547 }
548
549 int CMTerm1View::DrawBracket(CDC* pDC, int x0, int y0, int sizex, int sty, int sizey)
550 {
551     // TODO: 在此处添加实现代码.
552     int x1, y1, x2, y2;
553     // 左边的短横线
554     x1 = x0 ;
555     y1 = y0 + m_LinePosY;
556     x2 = x0 + 3;
557     y2 = y1;
558     pDC->MoveTo(x1, y1);
559     pDC->LineTo(x2, y2);
560
561     // 左方括号
562     x1 = x0 + 9;
563     y1 = y0 + sty;
564     x2 = x0 + 3;
565     y2 = y1;
566     pDC->MoveTo(x1, y1);
567     pDC->LineTo(x2, y2);
568     x2 = x2;
569     y2 = y2 + sizey;
570     pDC->LineTo(x2, y2);
571     x2 = x2 + 6;
572     y2 = y2;
573     pDC->LineTo(x2, y2);
574     // 右方括号
575     x1 = x0 + sizex - 6 - 6;
576     y1 = y0 + sty;
577     x2 = x0 + sizex -6 ;
578     y2 = y1;
579     pDC->MoveTo(x1, y1);
580     pDC->LineTo(x2, y2);
581     x2 = x2;
582     y2 = y2 + sizey;
583     pDC->LineTo(x2, y2);
584     x2 = x2 - 6;
585     y2 = y2;
586     pDC->LineTo(x2, y2);
587     // 右边的短横线
588     x1 = x0 + sizex - 6;
589     y1 = y0 + m_LinePosY;
590     x2 = x0 + sizex ;
591     y2 = y1;
592     pDC->MoveTo(x1, y1);
593     pDC->LineTo(x2, y2);
594     return 0;
595 }
d34256 596
418cb3 597 int CMTerm1View::DrawAngleBracket(CDC* pDC, int x0, int y0, int size1, int size2)
Q 598 {
599     // TODO: 在此处添加实现代码.
600     int x1,y1,x2, y2;
601     DrawLeftRightLine(pDC, x0, y0, size1, size2);
602     // 左尖括号
603     x1 = x0 + size1 + 6;
d34256 604     y1 = y0 + m_LinePosY -6; 
418cb3 605     x2 = x1 -6;
Q 606     y2 = y1 +6 ;
607     pDC->MoveTo(x1, y1);
608     pDC->LineTo(x2, y2);
609     x2 = x2 +6;
610     y2 = y2 + 6;
611     pDC->LineTo(x2, y2);
612     // 右尖括号
613     x1 = x0 + size1 + size2 - 6;
614     y1 = y0 + m_LinePosY - 6;
615     x2 = x1 + 6;
616     y2 = y1 + 6 ;
617     pDC->MoveTo(x1, y1);
618     pDC->LineTo(x2, y2);
619     x2 = x2 -6 ;
620     y2 = y2 + 6;
621     pDC->LineTo(x2, y2);
622     return 0;
623 }
624
625 int CMTerm1View::DrawCellStat1(CDC * pDC, int x1, int y1, int sizex, int sizey, int nStat)
626 {
627     // TODO: 在此处添加实现代码.
628     CRect rect1;
629     rect1.left = x1;
630     rect1.top = y1;
631     rect1.right = x1+sizex;
632     rect1.bottom = y1+sizey;
633
634     CBrush br0(BkColor);
635     CBrush br1(MonCoilColor);
636     if (m_bMonitoring) {
637         if (nStat) {
638             pDC->FillRect(&rect1, &br1);
639         }else{
640             pDC->FillRect(&rect1, &br0);
641         }
642     }
643     return 0;
644 }
645
646 int CMTerm1View::DrawCellStat2(CDC* pDC, int x1, int y1, int sizex, int sizey, int nStat)
647 {
648     // TODO: 在此处添加实现代码.
649     CRect rect1;
650     rect1.left = x1;
651     rect1.top = y1;
652     rect1.right = x1+sizex;
653     rect1.bottom = y1+sizey;
654     CBrush br2(TraceBkColor);
655     CBrush br3(TraceColor);
656     if (m_bMonitoring) {
657         if (nStat) {
658             pDC->FillRect(&rect1, &br3);
659         }else{
660             pDC->FillRect(&rect1, &br2);
661         }
662     }
663     return 0;
664 }
665
666 int CMTerm1View::DrawCellText1(CDC* pDC, CString sText, int x1, int y1, int sizex, int sizey, int nFormat)
667 {
668     // TODO: 在此处添加实现代码.
669     CRect rect1;
670     rect1.left = x1;
671     rect1.top = y1;
672     rect1.right = rect1.left + sizex;
673     rect1.bottom = rect1.top + sizey;
674     pDC->DrawText(sText, &rect1, nFormat);
675     return 0;
676 }
677
678 int CMTerm1View::DrawCellText2(CDC* pDC, CString sText, int x1, int y1, int sizex, int sizey, int nFormat, int nTextColor)
679 {
680     // TODO: 在此处添加实现代码.
681     COLORREF clrOld = pDC->SetTextColor(nTextColor);
682     CRect rect1;
683     rect1.left = x1;
684     rect1.top = y1;
685     rect1.right = rect1.left + sizex;
686     rect1.bottom = rect1.top + sizey;
687     pDC->DrawText(sText, &rect1, nFormat);
688     pDC->SetTextColor(clrOld);
689     return 0;
690 }
691
692 int CMTerm1View::DrawCellAnno(CDC * pDC, int nRow, int nCol, CString sAnno)
693 {
694     // TODO: 在此处添加实现代码.
695     if (!m_bShowComments) return 0;
696     if (!needReDraw) return 0;
697     CMTerm1Doc * pDoc = GetDocument();
698     int x0, y0;
699     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
700     x0 = m_LeftMargin + 1 + m_CellWidth * nCol;
701     y0 = m_TopMargin + CellTotalHeight * nRow;
702
703     int nType, nAddr;
704     nType = Cells[nRow][nCol].nDataType;
705     nAddr = Cells[nRow][nCol].nDataAddr;
706     CString s1;
707     if (pDoc->GetAnno(nType, nAddr, s1)) {
708         CFont *pOldFont;
709         pOldFont = (CFont *)pDC->SelectObject(&AnnoFont);
710         DrawCellText2(pDC, s1, x0 + 2, y0 + m_LinePosY + 6, m_CellWidth-10, 32, DT_WORDBREAK, AnnoColor);
711         pDC->SelectObject(pOldFont);
712     }
713     return 0;
714 }
715
716 void CMTerm1View::DrawCell(CDC* pDC, int nRow, int nCol)
717 {
718
719     //CMTerm1Doc * pDoc= GetDocument();
720     int x0, y0;
721     int x1, y1, x2, y2;
722     RECT rect1;
723     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
724
725     rect1.left = m_LeftMargin + 1 + m_CellWidth * nCol;
d34256 726     rect1.right = rect1.left + m_CellWidth; 
418cb3 727     rect1.top = m_TopMargin + CellTotalHeight * nRow;
Q 728     rect1.bottom = rect1.top + CellTotalHeight;
729
730     x0 = rect1.left;
731     y0 = rect1.top;
732
733     CString s1;
734     //    pDC->DrawFocusRect(&rect1);
735     if (Cells[nRow][nCol].bLeftLineUp && nCol !=0)
736     {
737         if (needReDraw) {
738             pDC->MoveTo(x0, y0);
739             pDC->LineTo(x0, y0 + m_LinePosY);
ad1b4b 740             //画直竖线
Z 741             //pDC->MoveTo(x0, y0 + (0.32 * CellTotalHeight));
742             //pDC->LineTo(x0, y0 - (0.69 * CellTotalHeight));
418cb3 743         }
Q 744     }
745     if (Cells[nRow][nCol].bLeftLineDn && nCol != 0)
746     {
747         if (needReDraw) {
748             pDC->MoveTo(x0, y0 + m_LinePosY);
749             pDC->LineTo(x0, y0 + CellTotalHeight);
750         }
751     }
752     int nType = Cells[nRow][nCol].nType;
753     if (nType == typeNone)
754     {
755
756     }
61deef 757     else if (nType == typeEND)    {
Q 758
759         if (needReDraw) {
760             //画左侧横线
761             //DrawLeftRightLine(pDC, x0, y0, 14, 18);
762             DrawAngleBracket(pDC, x0, y0, 8, 32);
763             DrawCellText1(pDC, _T("ED"), x0 + 16, y0 + m_LinePosY - 8, 24, 14);
764         }
765     }
418cb3 766     else if (nType == typeLine1)
Q 767     {    //Draw Line
768         //画直横线
769         if (needReDraw) {
770             pDC->MoveTo(x0, y0 + m_LinePosY);
771             pDC->LineTo(x0 + m_CellWidth, y0 + m_LinePosY);
772         }
773     }
774     else if (nType == typeLine2)
775     {    //Draw Line
ad1b4b 776         //画直竖线
6ff05a 777         pDC->MoveTo(x0, y0 + int(0.32 * CellTotalHeight));
Q 778         pDC->LineTo(x0, y0 - int(0.69 * CellTotalHeight));
418cb3 779     }
Q 780     else if (nType == typeNO)
781     {
782         // Draw Coil
783         if (needReDraw) {
784             DrawRelay(pDC, x0, y0);
785             //显示文字
786             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
787             DrawCellAnno(pDC, nRow, nCol, _T(""));
788         }
789         if (m_bMonitoring){
790             //Draw Stat
791             DrawCellStat1(pDC, x0 + 16 + 2, y0 + m_LinePosY - 6, 8, 12, Cells[nRow][nCol].nStat);
792             // tracing
793             DrawCellStat2(pDC, x0 + 16 + 2 + 10 + 4, y0 + m_LinePosY - 4, 4, 4, Cells[nRow][nCol].nTrace);
794         }
795     }
796     else if (nType == typeNC)
797     {
798         if (needReDraw) {
799             DrawRelay(pDC, x0, y0);
800             //显示文字
801             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
802             DrawCellAnno(pDC, nRow, nCol, _T(""));
803             //画常闭斜线
804             x1 = x0 + 16 + 12 - 3;
805             y1 = y0 + m_LinePosY - 6;
806             x2 = x0 + 16 + 2;
807             y2 = y1 + 12;
808             pDC->MoveTo(x1, y1);
809             pDC->LineTo(x2, y2);
810         }
811         if (m_bMonitoring)
812         {
813             //Draw Stat
814             DrawCellStat1(pDC, x0 + 16 + 2, y0 + m_LinePosY - 6, 8, 12, ! Cells[nRow][nCol].nStat);
815             // tracing
816             DrawCellStat2(pDC, x0 + 16 + 2 + 10 + 4, y0 + m_LinePosY - 4, 4, 4, Cells[nRow][nCol].nTrace);
817             //画常闭斜线
818             x1 = x0 + 16 + 12 - 3;
819             y1 = y0 + m_LinePosY - 6;
820             x2 = x0 + 16 + 2;
821             y2 = y1 + 12;
822             pDC->MoveTo(x1, y1);
823             pDC->LineTo(x2, y2);
824         }
825     }
826     else if (nType == typePP)
827     {
828         if (needReDraw) {
829             DrawRelay(pDC, x0, y0);
830             //画上升沿箭头
831             x1 = x0 + 16 + 6;
832             y1 = y0 + m_LinePosY - 5;
833             x2 = x1;
834             y2 = y1 + 10;
835             pDC->MoveTo(x1, y1);
836             pDC->LineTo(x2, y2);
837             //*
838             x2 = x1 - 3;
839             y2 = y1 + 4;
840             pDC->MoveTo(x1, y1);
841             pDC->LineTo(x2, y2);
842             x2 = x1 + 3;
843             y2 = y1 + 4;
844             pDC->MoveTo(x1, y1);
845             pDC->LineTo(x2, y2);
846             //*/
847                     //显示文字
848             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
849             DrawCellAnno(pDC, nRow, nCol, _T(""));
850         }
851     }
852     else if (nType == typePN)
853     {
854         if (needReDraw) {
855             DrawRelay(pDC, x0, y0);
856             //画下降沿箭头
857             x1 = x0 + 16 + 6;
858             y1 = y0 + m_LinePosY + 5;
859             x2 = x1;
860             y2 = y1 - 10;
861             pDC->MoveTo(x1, y1);
862             pDC->LineTo(x2, y2);
863             //*
864             x2 = x1 - 3;
865             y2 = y1 - 3;
866             pDC->MoveTo(x1, y1);
867             pDC->LineTo(x2, y2);
868
869             x2 = x1 + 3;
870             y2 = y1 - 3;
871             pDC->MoveTo(x1, y1);
872             pDC->LineTo(x2, y2);
873             //*/
874             //显示文字
875             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
876             DrawCellAnno(pDC, nRow, nCol, _T(""));
877         }
878     }
879     else if (nType == typeNOT)    {
880         if (needReDraw) {
881             DrawLeftRightLine(pDC, x0, y0);
882             //画常闭斜线
883             x1 = x0 + 16 + 12 - 3;
884             y1 = y0 + m_LinePosY - 6;
885             x2 = x0 + 16 + 2;
886             y2 = y1 + 12;
887             pDC->MoveTo(x1, y1);
888             pDC->LineTo(x2, y2);
889             //显示文字
890     //        DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
891         }
892     }
893     else if (nType == typeDF)    {
894         if (needReDraw) {
895             //    DrawLeftRightLine(pDC, x0, y0);
896             DrawAngleBracket(pDC, x0, y0, 8, 32);
897             //显示文字
898             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 16, y0 + m_LinePosY - 8, 16, 14);
899         }
900     }
901     else if (nType == typeDF_)    {
902         if (needReDraw) {
903             //    DrawLeftRightLine(pDC, x0, y0);
904             DrawAngleBracket(pDC, x0, y0, 8, 40);
905             //显示文字
906             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 16, y0 + m_LinePosY - 8, 24, 14);
907         }
908     }
909     else if (nType == typeOUT)    {
910         if (needReDraw) {
911             //显示外形
912             DrawOT(pDC, x0, y0);
913             //显示文字
914             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
915             DrawCellAnno(pDC, nRow, nCol, _T(""));
916         }
917         if (m_bMonitoring) {
918             //Draw Stat
919             DrawCellStat1(pDC, x0 + 16 + 2, y0 + m_LinePosY - 6, 8, 12, Cells[nRow][nCol].nStat);
920         }
921     }
922     else if (nType == typeSET)    {
923
924         if (needReDraw) {
925             //画左侧横线
926             //DrawLeftRightLine(pDC, x0, y0, 14, 18);
927             DrawAngleBracket(pDC, x0, y0, 8, 32);
928             DrawCellText1(pDC, _T("S"), x0 + 18, y0 + m_LinePosY - 8, 8, 14);
929             //显示文字
930             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
931             DrawCellAnno(pDC, nRow, nCol, _T(""));
932         }
933         if (m_bMonitoring) {
934             //Draw Stat
935             DrawCellStat1(pDC, x0 + 14, y0 + m_LinePosY - 8, 16, 16, Cells[nRow][nCol].nStat);
936             DrawCellText1(pDC, _T("S"), x0 + 18, y0 + m_LinePosY - 8, 8, 14);
937         }
938
939     }
940     else if (nType == typeRESET)    {
941         if (needReDraw) {
942             //画左右侧横线
943             //DrawLeftRightLine(pDC, x0, y0, 14, 18);
944             DrawAngleBracket(pDC, x0, y0, 8, 32);
945             DrawCellText1(pDC, _T("R"), x0 + 17, y0 + m_LinePosY - 8, 9, 14);
946             //显示文字
947             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 2, y0, m_CellWidth, 14);
948             DrawCellAnno(pDC, nRow, nCol, _T(""));
949         }
950         if (m_bMonitoring) {
951             //Draw Stat
952             DrawCellStat1(pDC, x0 + 14, y0 + m_LinePosY - 8, 16, 16, Cells[nRow][nCol].nStat);
953             DrawCellText1(pDC, _T("R"), x0 + 17, y0 + m_LinePosY - 8, 9, 14);
954         }
955     }
956     else if (nType == typeCMP)    {
957         if (needReDraw) {
958             // 画中括号
959             DrawBracket(pDC, x0, y0, m_CellWidth * 3);
960             //显示文字
961             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 12, y0, m_CellWidth, 14);
962             DrawCellText1(pDC, Cells[nRow][nCol + 1].sParam, x0 + m_CellWidth + 2, y0, m_CellWidth, 14);
963             DrawCellText1(pDC, Cells[nRow][nCol + 2].sParam, x0 + m_CellWidth * 2 + 2, y0, m_CellWidth, 14);
964             DrawCellAnno(pDC, nRow, nCol + 1, _T(""));
965             DrawCellAnno(pDC, nRow, nCol + 2, _T(""));
966         }
967         if (m_bMonitoring) {
968             s1.Format(_T("     %d"), Cells[nRow][nCol + 1].nStat);
969             DrawCellText2(pDC, s1,x0+m_CellWidth+2,y0+m_LinePosY-6,m_CellWidth-10,14,DT_RIGHT, MonTextColor);
970             s1.Format(_T("     %d"), Cells[nRow][nCol + 2].nStat);
971             DrawCellText2(pDC, s1, x0 + m_CellWidth*2 + 2, y0 + m_LinePosY - 6, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
972             // tracing
973             DrawCellStat2(pDC, x0 + m_CellWidth * 3 - 4, y0 + m_LinePosY - 8, 4, 4, Cells[nRow][nCol].nTrace);
974         }
975     }
976     else if (nType == typeTM)    {
977         if (needReDraw) {
978             // 画中括号
979             DrawBracket(pDC, x0, y0, m_CellWidth * 3);
980             //显示文字
981             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 12, y0, m_CellWidth, 14);
982             DrawCellText1(pDC, Cells[nRow][nCol + 1].sParam, x0 + m_CellWidth + 2, y0, m_CellWidth, 14);
983             DrawCellText1(pDC, Cells[nRow][nCol + 2].sParam, x0 + m_CellWidth * 2 + 2, y0, m_CellWidth, 14);
984             DrawCellAnno(pDC, nRow, nCol, _T(""));
985             DrawCellAnno(pDC, nRow, nCol + 1, _T(""));
986             DrawCellAnno(pDC, nRow, nCol + 2, _T(""));
987         }
988         if (m_bMonitoring) {
989             s1.Format(_T("     %d"), Cells[nRow][nCol + 1].nStat);
990             DrawCellText2(pDC, s1, x0 + m_CellWidth + 2, y0 + m_LinePosY - 6, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
991             s1.Format(_T("     %d"), Cells[nRow][nCol + 2].nStat);
992             DrawCellText2(pDC, s1, x0 + m_CellWidth * 2 + 2, y0 + m_LinePosY - 6, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
993             // tracing
994             DrawCellStat2(pDC, x0 + m_CellWidth * 3 - 4, y0 + m_LinePosY - 8, 4, 4, Cells[nRow][nCol].nTrace);
995         }
996     }
997     else if (nType == typeFN1)    {
998         if (needReDraw) {
999
1000             // 画中括号
1001             DrawBracket(pDC, x0, y0, m_CellWidth * 2, m_LinePosY - 8, 16);
1002             //显示文字
1003             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 12, y0 + m_LinePosY - 6, m_CellWidth, 14);
1004             DrawCellText1(pDC, Cells[nRow][nCol + 1].sParam, x0 + m_CellWidth + 2, y0 + m_LinePosY - 6, m_CellWidth, 14);
1005             DrawCellAnno(pDC, nRow, nCol + 1, _T(""));
1006         }
1007         if (m_bMonitoring) {
1008
1009             s1.Format(_T("     %d"), Cells[nRow][nCol + 1].nStat);
1010             DrawCellText2(pDC, s1, x0 + m_CellWidth + 2, y0 , m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
1011             // tracing
1012             DrawCellStat2(pDC, x0 + m_CellWidth * 2 - 4, y0 + m_LinePosY - 8, 4, 4, Cells[nRow][nCol].nTrace);
1013         }
1014     }
1015     else if (nType == typeFN2)    {
1016         if (needReDraw) {
1017             // 画中括号
1018             DrawBracket(pDC, x0, y0, m_CellWidth * 3, m_LinePosY - 8, 16);
1019             //显示文字
1020             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 12, y0 + m_LinePosY - 6, m_CellWidth, 14);
1021             DrawCellText1(pDC, Cells[nRow][nCol + 1].sParam, x0 + m_CellWidth + 2, y0 + m_LinePosY - 6, m_CellWidth, 14);
1022             DrawCellText1(pDC, Cells[nRow][nCol + 2].sParam, x0 + m_CellWidth * 2 + 2, y0 + m_LinePosY - 6, m_CellWidth, 14);
1023             DrawCellAnno(pDC, nRow, nCol + 1, _T(""));
1024             DrawCellAnno(pDC, nRow, nCol + 2, _T(""));
1025         }
1026         if (m_bMonitoring) {
1027             s1.Format(_T("     %d"), Cells[nRow][nCol + 1].nStat);
1028             DrawCellText2(pDC, s1, x0 + m_CellWidth + 2, y0, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
1029             s1.Format(_T("     %d"), Cells[nRow][nCol + 2].nStat);
1030             DrawCellText2(pDC, s1, x0 + m_CellWidth * 2 + 2, y0, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
1031             // tracing
1032             DrawCellStat2(pDC, x0 + m_CellWidth * 3 - 4, y0 + m_LinePosY - 8, 4, 4, Cells[nRow][nCol].nTrace);
1033         }
1034     }
1035     else if (nType == typeFN3)    {
1036         if (needReDraw) {
1037             // 画中括号
1038             DrawBracket(pDC, x0, y0, m_CellWidth * 4, m_LinePosY - 8, 16);
1039             //显示文字
1040             DrawCellText1(pDC, Cells[nRow][nCol].sCoilName, x0 + 12, y0 + m_LinePosY - 6, m_CellWidth, 14);
1041             DrawCellText1(pDC, Cells[nRow][nCol + 1].sParam, x0 + m_CellWidth + 2, y0 + m_LinePosY - 6, m_CellWidth, 14);
1042             DrawCellText1(pDC, Cells[nRow][nCol + 2].sParam, x0 + m_CellWidth * 2 + 2, y0 + m_LinePosY - 6, m_CellWidth, 14);
1043             DrawCellText1(pDC, Cells[nRow][nCol + 3].sParam, x0 + m_CellWidth * 3 + 2, y0 + m_LinePosY - 6, m_CellWidth, 14);
1044             DrawCellAnno(pDC, nRow, nCol + 1, _T(""));
1045             DrawCellAnno(pDC, nRow, nCol + 2, _T(""));
1046             DrawCellAnno(pDC, nRow, nCol + 3, _T(""));
1047         }
1048         if (m_bMonitoring) {
1049             s1.Format(_T("     %d"), Cells[nRow][nCol + 1].nStat);
1050             DrawCellText2(pDC, s1, x0 + m_CellWidth + 2, y0, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
1051             s1.Format(_T("     %d"), Cells[nRow][nCol + 2].nStat);
1052             DrawCellText2(pDC, s1, x0 + m_CellWidth * 2 + 2, y0, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
1053             s1.Format(_T("     %d"), Cells[nRow][nCol + 3].nStat);
1054             DrawCellText2(pDC, s1, x0 + m_CellWidth * 3 + 2, y0, m_CellWidth - 10, 14, DT_RIGHT, MonTextColor);
1055             // tracing
1056             DrawCellStat2(pDC, x0 + m_CellWidth * 4 - 4, y0 + m_LinePosY - 8, 4, 4, Cells[nRow][nCol].nTrace);
1057         }
1058     }
1059     else
1060     {
1061     }
1062 }
0ed438 1063
Q 1064 // CMTerm1View 消息处理程序
418cb3 1065
Q 1066 void CMTerm1View::OnUpdate(CView* /*pSender*/, LPARAM lHint, CObject* /*pHint*/)
1067 {
1068     // TODO: 在此添加专用代码和/或调用基类
1069     //初始化 cell 内容 
1070     if (lHint == 0 || lHint == 1)
1071     {
1072         TransProgToLDS();
1073         CRect rect0;
1074         this->GetClientRect(&rect0);
1075
1076         int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1077
1078         CSize sizeTotal;
1079         // TODO: 计算此视图的合计大小
1080         sizeTotal.cx = m_LeftMargin + m_CellWidth * m_CellPerLine + m_CellWidth * 2;
1081         sizeTotal.cy = m_TopMargin + CellTotalHeight * (m_nTotalRow - 1) + rect0.Height();
1082         SetScrollSizes(MM_TEXT, sizeTotal);
1083         needReDraw = 1;
1084         this->RedrawWindow();
1085     }
1086     else if (lHint == 2) {
1087         UpdateStatusBar();
1088     }
1089
1090 }
1091
1092 BOOL CMTerm1View::OnEraseBkgnd(CDC* pDC)
1093 {
1094     // TODO: 在此添加消息处理程序代码和/或调用默认值
1095     return true;
1096     return CScrollView::OnEraseBkgnd(pDC);
1097 }
1098
1099 void CMTerm1View::OnSize(UINT nType, int cx, int cy)
1100 {
1101     CScrollView::OnSize(nType, cx, cy);
1102 //    CString s1;
1103 //    s1.Format(_T("OnSize %d %d %d"), nType, cx, cy);
1104 //    DbgLog(s1);
1105
1106     if (this->IsWindowVisible())
1107     {
1108         CRect rect0;
1109         this->GetClientRect(&rect0);
1110
1111         int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1112
1113         CSize sizeTotal;
1114         // TODO: 计算此视图的合计大小
1115         sizeTotal.cx = m_LeftMargin + m_CellWidth * m_CellPerLine + m_CellWidth * 2;
1116         sizeTotal.cy = m_TopMargin + CellTotalHeight * (m_nTotalRow - 1) + rect0.Height();
1117         SetScrollSizes(MM_TEXT, sizeTotal);
1118         needReDraw = 1;
1119         this->RedrawWindow();
1120     }
1121
1122     needReDraw = 1;
1123     // TODO: 在此处添加消息处理程序代码
1124 }
1125
1126 BOOL CMTerm1View::OnScrollBy(CSize sizeScroll, BOOL bDoScroll)
1127 {
1128     // TODO: 在此添加专用代码和/或调用基类
1129     needReDraw = 1;
1130     return CScrollView::OnScrollBy(sizeScroll, bDoScroll);
1131 }
1132
1133 void CMTerm1View::OnKeyDown(UINT nChar, UINT nRepCnt, UINT nFlags)
1134 {
1135     // TODO: 在此添加消息处理程序代码和/或调用默认值
1136     CString s1;
1137 //    s1.Format(_T("KeyDown %d %d %d"), nChar, nRepCnt, nFlags);
1138 //    DbgLog(s1);
1139     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1140
1141     CRect rect0;
1142     this->GetClientRect(&rect0);
1143     int viewWidth = rect0.Width();
1144     CPoint scroll1;
1145     scroll1 = this->GetScrollPosition();
1146
1147     int nFirstVisibleLine;
1148     int nLastVisibleLine;
1149     int nLinesinView;
1150     nFirstVisibleLine = (scroll1.y - m_TopMargin) / CellTotalHeight;
1151     nLastVisibleLine = (rect0.Height() + scroll1.y - m_TopMargin) / CellTotalHeight + 1;
1152     if (nFirstVisibleLine < 0) { nFirstVisibleLine = 0; }
1153     if (nLastVisibleLine < 0) { nLastVisibleLine = 0; }
1154     nLinesinView = nLastVisibleLine - 1 - nFirstVisibleLine;
1155     int nRow, nCol;
1156     nRow = m_FocusRow;
1157     nCol = m_FocusCol;
1158     if (nChar == VK_LEFT) {
1159         nCol -= 1;
1160         if (nCol < 0) { 
1161             if (nRow > 0) {
1162                 nRow -= 1; nCol += m_CellPerLine;
1163             }else { 
1164                 nCol = 0; 
1165             }
1166         }
4ed7fc 1167         CellFocusChg(nRow, nCol);
418cb3 1168     }
Q 1169     if (nChar == VK_RIGHT) {
1170         nCol += 1;
1171         if (nCol >= m_CellPerLine) { 
1172             if (nRow < m_nTotalRow + nLinesinView - 1 ) {
1173                 nCol -= m_CellPerLine;
1174                 nRow += 1;
1175             }
1176             else {
1177                 nCol = m_CellPerLine - 1;
1178             }
1179         }
4ed7fc 1180         CellFocusChg(nRow, nCol);
418cb3 1181     }
Q 1182     if (nChar == VK_UP) {
1183         nRow -= 1;
1184         if (nRow < 0) { nRow = 0; }
4ed7fc 1185         CellFocusChg(nRow, nCol);
418cb3 1186     }
Q 1187     if (nChar == VK_DOWN) {
1188         nRow += 1;
1189         if (nRow >= m_nTotalRow + nLinesinView) { nRow = m_nTotalRow + nLinesinView -1; }
4ed7fc 1190         CellFocusChg(nRow, nCol);
418cb3 1191     }
Q 1192     m_FocusRow = nRow;
1193     m_FocusCol = nCol;
1194     if (Cells[nRow][nCol].nType) {
1195         m_nCurProgStep = Cells[nRow][nCol].nProgStep;
1196     }
1197     
1198     if (nRow < nFirstVisibleLine) { 
1199         scroll1.y -= CellTotalHeight;
1200         ScrollToPosition(scroll1); 
1201     }
1202     if (nRow > 0 && nRow >= nLastVisibleLine - 1 ) { 
1203         scroll1.y += CellTotalHeight;
1204         ScrollToPosition(scroll1); 
1205     }
1206
1207     //    DrawFocusRect();
1208     GetDocument()->UpdateAllViews(this, m_FocusCol);
1209     needReDraw = 1;
1210     this->RedrawWindow();
1211     UpdateStatusBar();
1212
1213     CScrollView::OnKeyDown(nChar, nRepCnt, nFlags);
1214 }
d34256 1215
Z 1216 /// <summary>
1217 /// 单元格焦点变化*选中点变化
1218 /// </summary>
1219 /// <param name="nRow"></param>
1220 /// <param name="nCol"></param>
1221 /// <returns></returns>
df0321 1222 int CMTerm1View::CellFocusChg(int nRow, int nCol)
Q 1223 {
1224     CString s1;
1225     stCell & thecell = Cells[nRow][nCol];
6ff05a 1226     s1.Format(_T("Cell %d %d Type %02X OpType %02X \r\n"), nRow, nCol, thecell.nType,thecell.nOpType);
df0321 1227     s1.AppendFormat(_T(" sCoilName %s sParam %s \r\n"), thecell.sCoilName, thecell.sParam );
Q 1228     s1.AppendFormat(_T("LeftUp %d leftDn %d "), thecell.bLeftLineUp, thecell.bLeftLineDn);
1229     DbgLog(s1);
1230
1231     auto p1 = (CMainFrame*)AfxGetMainWnd();
1232     auto p2 = p1->GetInputWnd();
ad1b4b 1233         p2->SetCurCellPos(nRow,nCol,thecell);
Z 1234         p2->focusCell = thecell;
df0321 1235     return 0;
Q 1236 }
ad1b4b 1237 //鼠标左键点击事件
418cb3 1238 void CMTerm1View::OnLButtonDown(UINT nFlags, CPoint point)
Q 1239 {
1240     // TODO: 在此添加消息处理程序代码和/或调用默认值
1241     CString s1;
1242     CPoint scroll1;
1243     scroll1 = this->GetScrollPosition();
1244     int tx, ty;
1245     tx = point.x + scroll1.x;
1246     ty = point.y + scroll1.y;
1247     int nRow, nCol;
1248     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1249     nRow = (ty - m_TopMargin) / CellTotalHeight;
1250     nCol = (tx - m_LeftMargin) / m_CellWidth;
d34256 1251     if (nRow < 0) 
Z 1252     {
1253         nRow = 0; 
1254     }
1255     if (nCol < 0) 
1256     { 
1257         nCol = 0; 
1258     }
1259     if (nCol >= m_CellPerLine) 
1260     {
1261         nCol = m_CellPerLine - 1; 
1262     }
1263     s1.Format(_T("OnLButtonDown::zxd:: LD %d %d  %02X  Scroll %d %d  Total %d %d Row %d Col %d"), point.x, point.y, nFlags, scroll1.x, scroll1.y, tx, ty, nRow, nCol);
1264     DbgLog(s1);//zxd add to test
1265
418cb3 1266     m_pStatusBar->SetPaneText(6, s1);
Q 1267     m_FocusRow = nRow;
1268     m_FocusCol = nCol;
1269     if (Cells[nRow][nCol].nType) {
1270         m_nCurProgStep = Cells[nRow][nCol].nProgStep;
1271     }
1272
1273     //    DrawFocusRect();
df0321 1274     CellFocusChg(nRow, nCol);
418cb3 1275     GetDocument()->UpdateAllViews(this, m_FocusCol);
Q 1276     needReDraw = 1;
1277     this->RedrawWindow();
1278     UpdateStatusBar();
1279     //    m_pStatusBar->Set
1280     CScrollView::OnLButtonDown(nFlags, point);
1281 }
1282
1283 void CMTerm1View::OnLButtonUp(UINT nFlags, CPoint point)
1284 {
1285     // TODO: 在此添加消息处理程序代码和/或调用默认值
1286
1287     CScrollView::OnLButtonUp(nFlags, point);
1288 }
1289
1290 void CMTerm1View::OnLButtonDblClk(UINT nFlags, CPoint point)
1291 {
1292     // TODO: 在此添加消息处理程序代码和/或调用默认值
1293     CString s1;
1294     CMTerm1Doc * pDoc = (CMTerm1Doc*)GetDocument();
1295     CPoint scroll1;
1296     scroll1 = this->GetScrollPosition();
1297     int tx, ty;
1298     tx = point.x + scroll1.x;
1299     ty = point.y + scroll1.y;
1300
1301     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1302     int nRow = (ty - m_TopMargin) / CellTotalHeight;
1303     int nCol = (tx - m_LeftMargin) / m_CellWidth;
1304
1305     if (nRow < 0) { nRow = 0; }
1306     if (nCol < 0) { nCol = 0; }
1307     if (nCol >= m_CellPerLine) { nCol = m_CellPerLine - 1; }
1308     s1.Format(_T("LD db Clk %d %d  %02X  Scroll %d %d  Total %d %d Row %d Col %d"),
1309         point.x, point.y, nFlags, scroll1.x, scroll1.y, tx, ty, nRow, nCol);
1310     m_pStatusBar->SetPaneText(6, s1);
1311     m_pStatusBar->SetPaneBackgroundColor(6, RGB(255, 255, 0));
1312     m_pStatusBar->SetPaneTextColor(6, RGB(0, 0, 255));
1313     m_pStatusBar->EnablePaneProgressBar(6);
1314     m_pStatusBar->SetPaneProgress(6, 5);
1315     SysLog(s1);
1316
1317     m_FocusRow = nRow;
1318     m_FocusCol = nCol;
1319     if (Cells[nRow][nCol].nType) {
1320         m_nCurProgStep = Cells[nRow][nCol].nProgStep;
1321     }
1322     if (!pDoc->m_bOnline) return;
61deef 1323     if (!m_bMonitoring || !pDoc->m_bOnline) {
Q 1324     
1325     };
1326     
418cb3 1327     CString sParam;
Q 1328     sParam = Cells[nRow][nCol].sParam;
1329     int nDataType, nDataAddr, nStat;
1330     nDataType = Cells[nRow][nCol].nDataType;
1331     nDataAddr = Cells[nRow][nCol].nDataAddr;
1332     nStat = Cells[nRow][nCol].nStat;
1333
1334     s1.Format(_T("Name %s DataType %d DataAddr %d  Stat %d"),
1335         sParam, nDataType, nDataAddr, nStat);
1336     SysLog(s1);
1337     if (Cells[m_FocusRow][m_FocusCol].sParam == _T("")) {
1338         return;
1339     }
1340     needReDraw = 1;
1341     if ((nDataType&TYPEDATA) == TYPEDATA) {
1342         CDialogSetData dialog2;
1343
1344         dialog2.m_strAddr = sParam;
1345         dialog2.m_nStat = nStat;
1346
1347         INT_PTR r = dialog2.DoModal();
1348         if (r == IDOK)
1349         {
1350             int s = dialog2.m_nStat;
1351             ///
1352             pDoc->SetVarData(nDataType, nDataAddr, s);
1353             //Cells[nRow][nCol].nStat = s;
1354             s1.Format(_T("Set Data %s as %d "), sParam, s);
1355             SysLog(s1);
1356             this->RedrawWindow();
1357         }
1358     }
1359     else {
1360         CDialogSetCoil dialog1;
1361
1362         dialog1.m_strAddr = sParam;
1363         dialog1.m_nStat = nStat;
1364
1365         INT_PTR r = dialog1.DoModal();
1366         if (r == IDOK)
1367         {
1368             int s = dialog1.m_nStat;
1369             ///
1370             pDoc->SetCoilValue(nDataType, nDataAddr, s);
1371             //        Cells[nRow][nCol].nStat = nStat;
1372
1373             //        Cells[m_FocusRow][m_FocusCol].nStat = s;
1374             //        s1.Format(_T("Set Coild %s as %d "), sParam, s);
1375             //        AfxMessageBox(s1);
1376             this->RedrawWindow();
1377         }
1378     }
1379     CScrollView::OnLButtonDblClk(nFlags, point);
1380 }
1381
1382 void CMTerm1View::OnRButtonDown(UINT nFlags, CPoint point)
1383 {
1384     // TODO: 在此添加消息处理程序代码和/或调用默认值
1385     CString s1;
1386     CPoint scroll1;
1387     scroll1 = this->GetScrollPosition();
1388     int tx, ty;
1389     tx = point.x + scroll1.x;
1390     ty = point.y + scroll1.y;
1391
1392     int nRow, nCol;
1393     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1394     nRow = (ty- m_TopMargin )/ CellTotalHeight;
1395     nCol = (tx - m_LeftMargin) / m_CellWidth;
1396
1397     if (nRow < 0) { nRow = 0; }
1398     if (nCol < 0) { nCol = 0; }
1399     if (nCol >= m_CellPerLine) { nCol = m_CellPerLine - 1; }
1400     s1.Format(_T("RD %d %d  %02X  Scroll %d %d  Total %d %d Row %d Col %d"), point.x, point.y, nFlags, scroll1.x, scroll1.y, tx, ty, m_FocusRow, m_FocusCol);
1401     m_pStatusBar->SetPaneText(6, s1);
1402     m_FocusRow = nRow;
1403     m_FocusCol = nCol;
1404     //    DrawFocusRect();
1405     GetDocument()->UpdateAllViews(this, m_FocusCol);
1406     needReDraw = 1;
1407     this->RedrawWindow();
1408
1409     CScrollView::OnRButtonDown(nFlags, point);
1410 }
1411
1412 void CMTerm1View::OnRButtonUp(UINT nFlags, CPoint point)
1413 {
1414     // TODO: 在此添加消息处理程序代码和/或调用默认值
1415     //CContextMenuManager
1416     CScrollView::OnRButtonUp(nFlags, point);
1417 }
1418
1419 void CMTerm1View::OnContextMenu(CWnd* /*pWnd*/, CPoint point)
1420 {
1421     // TODO: 在此处添加消息处理程序代码
1422     CMenu menu1;
1423     menu1.LoadMenu(IDR_MENU1);
1424     CMenu *pContextMenu = menu1.GetSubMenu(0);
1425     pContextMenu->TrackPopupMenu(TPM_LEFTALIGN | TPM_RIGHTBUTTON, point.x, point.y, this);
1426 }
1427
1428 void CMTerm1View::OnInitMenuPopup(CMenu* pPopupMenu, UINT nIndex, BOOL bSysMenu)
1429 {
1430     CScrollView::OnInitMenuPopup(pPopupMenu, nIndex, bSysMenu);
1431
1432     // TODO: 在此处添加消息处理程序代码
1433     if (!bSysMenu && pPopupMenu)
1434     {
1435         CCmdUI cmdUI;
1436         cmdUI.m_pOther = NULL;
1437         cmdUI.m_pMenu = pPopupMenu;
1438         cmdUI.m_pSubMenu = NULL;
1439
1440
1441         UINT count = pPopupMenu->GetMenuItemCount();
1442         cmdUI.m_nIndexMax = count;
1443         for (UINT i = 0; i < count; i++)
1444         {
1445             UINT nID = pPopupMenu->GetMenuItemID(i);
1446             if (-1 == nID || 0 == nID)
1447             {
1448                 continue;
1449             }
1450             cmdUI.m_nID = nID;
1451             cmdUI.m_nIndex = i;
1452             cmdUI.DoUpdate(this, FALSE);
1453         }
1454     }
1455 }
1456
1457 void CMTerm1View::OnTimer(UINT_PTR nIDEvent)
1458 {
1459     // TODO: 在此添加消息处理程序代码和/或调用默认值
1460     CString s1;
1461     CMTerm1Doc * pDoc = (CMTerm1Doc*)GetDocument();
61deef 1462     static int nCount = 0;
418cb3 1463     if (nIDEvent == 0) {
Q 1464
1465     }
1466     else if (nIDEvent == 1)
1467     {
61deef 1468         nCount++;
Q 1469         if (m_bMonitoring && (nCount &1)) {
418cb3 1470             //this->RedrawWindow();
Q 1471             DoReDraw();
1472         }
1473     }
1474     else if (nIDEvent == 2) {
1475         pDoc->OnTimer(2);
1476     }
1477     else {
1478
1479     }
1480     CScrollView::OnTimer(nIDEvent);
1481 }
1482
1483 void CMTerm1View::OnMonitor()
1484 {
1485     // TODO: 在此添加命令处理程序代码
1486     m_bMonitoring = !m_bMonitoring;
1487     this->RedrawWindow();
1488     UpdateStatusBar();
1489 }
1490
1491 void CMTerm1View::OnUpdateMonitor(CCmdUI *pCmdUI)
1492 {
1493     // TODO: 在此添加命令更新用户界面处理程序代码
1494     pCmdUI->SetCheck(m_bMonitoring == true);
1495 }
1496
ad1b4b 1497 /// <summary>
Z 1498 /// 程序转换按钮点击
1499 /// </summary>
418cb3 1500 void CMTerm1View::OnProgConvert()
Q 1501 {
e55aec 1502     //转换前先对LDS的规则进行检验(检验规则与返回参数并未完全确定
4ed7fc 1503  //    std::pair<int,CString> result = LDSCheckRule();
Z 1504     //if (result.first == 111)
1505     //{
1506     //    DbgLog(result.second);
1507     //    return;
1508     //}
e55aec 1509
418cb3 1510     CString s1;
Q 1511     s1.Format(_T("Prog Convert"));
4ed7fc 1512      SysLog(s1);
6ff05a 1513     int r = TransLDSToProgAOV();  //TransLDSToProg();
418cb3 1514     s1.Format(_T("LDS To Prog result %d"), r);
Q 1515     SysLog(s1);
6ff05a 1516 ///*
e55aec 1517     if (r==0) 
Z 1518     {
418cb3 1519     //    m_bModified = 0;
6ff05a 1520         GetDocument()->FindProgPair();
Q 1521         GetDocument()->TransProgToBin();
418cb3 1522         int j=TransProgToLDS();
Q 1523         s1.Format(_T("Porg to LDS retuls %d"), j);
1524         SysLog(s1);
1525         needReDraw = 1;
1526         RedrawWindow();
1527     }
1528     else {
1529         s1.Format(_T("Error in Prog Convert"));
1530         SysLog(s1);
1531     }
6ff05a 1532 //*/
418cb3 1533 }
Q 1534
1535 void CMTerm1View::OnUpdateProgConvert(CCmdUI *pCmdUI)
1536 {
1537     // TODO: 在此添加命令更新用户界面处理程序代码
1538     pCmdUI->SetCheck(0);
1539     pCmdUI->Enable(m_bModified);
1540 }
1541
1542 void CMTerm1View::OnProgCancelEdit()
1543 {
1544     CString s1;
1545     s1.Format(_T("Prog Cancel Edit"));
1546     SysLog(s1);
1547     // TODO: 在此添加命令处理程序代码
1548 }
1549
1550
1551 void CMTerm1View::OnUpdateProgCancelEdit(CCmdUI *pCmdUI)
1552 {
1553     // TODO: 在此添加命令更新用户界面处理程序代码
1554 //    pCmdUI->SetCheck(m_bModified);
1555     pCmdUI->Enable(m_bModified);
1556 }
1557
1558
1559 void CMTerm1View::OnInsertBlankLine()
1560 {
1561     // TODO: 在此添加命令处理程序代码
1562     CString s1;
1563     s1.Format(_T("Insert Blank Line"));
1564     SysLog(s1);
1565     m_FocusRow;
1566     //当前行之后的所有,下移一行
1567     for (int i = m_nTotalRow - 1; i >= m_FocusRow; i--) {
1568         for (int j = 0; j < m_CellPerLine; j++) {
1569             Cells[i + 1][j] = Cells[i][j];
1570         }
1571     }
1572     m_nTotalRow += 1;
1573     // 当前行灰色    
1574     for (int j = 0; j < m_CellPerLine; j++)    {
1575         Cells[m_FocusRow][j].clear();
1576         Cells[m_FocusRow][j].bEditing = 1;
1577         Cells[m_FocusRow][j].bModified = 1;
1578         if (Cells[m_FocusRow + 1][j].bLeftLineUp) {
1579             Cells[m_FocusRow][j].bLeftLineUp = 1;
1580             Cells[m_FocusRow][j].bLeftLineDn = 1;
1581         }
1582     }
1583
1584     // 当前行 加入 触点
1585 //    m_FocusCol;
1586 //    Cells[m_FocusRow][0].nType= typeNO;
1587 //    Cells[m_FocusRow][0].nDataType = KLCoilTypeX;
1588 //    Cells[m_FocusRow][0].nDataAddr = 15;
1589 //    Cells[m_FocusRow][0].sCoilName = "ABCDEFG";
1590
1591     m_bModified = 1;
1592     needReDraw = 1;
1593     this->RedrawWindow();
1594 }
1595 int FindTypeIndex(CString str[], CString strType, int num)
1596 {
1597     for (int i = 0;i < num;i++)
1598     {
1599         if (strType == str[i])
1600         {
1601             return i;
1602         }
1603     }
1604     return -1;
1605 }
1606
ad1b4b 1607 /// <summary>
Z 1608 /// 设置Cell到窗口视图
1609 /// </summary>
1610 /// <param name="cell1"></param>
1611 void CMTerm1View::SetCellToView(stCell cell1, int flag)               //**************************************************************************************************//
418cb3 1612 {
4ed7fc 1613     bool changeVLine = false;
Z 1614     if ((Cells[m_FocusRow][m_FocusCol].bLeftLineDn != cell1.bLeftLineDn) 
1615         || (Cells[m_FocusRow][m_FocusCol].bLeftLineUp != cell1.bLeftLineUp))
1616     {
1617         changeVLine = true;
1618     }
418cb3 1619     Cells[m_FocusRow][m_FocusCol] = cell1;
Q 1620     m_bModified = 1;
1621     needReDraw = 1;
ad1b4b 1622     
df0321 1623     Cells[m_FocusRow][0].bEditing = 1;
Q 1624
ad1b4b 1625     if (m_nTotalRow < m_FocusRow + 1) 
Z 1626     {
df0321 1627         m_nTotalRow = m_FocusRow + 1;
Q 1628     }
ad1b4b 1629     //单元格关联修改
Z 1630     switch (flag)
1631     {
1632     case 1:
1633     {
1634         if(Cells[m_FocusRow - 1][m_FocusCol].nType == CMTerm1View::typeExt1)
1635         {
1636             //发送错误信息
1637             DbgLog(_T("插入纵线失败:光标位置错误!参数位置不允许添加纵线"));
1638             return;
1639         }
1640         //添加纵线时同步添加上一行
1641         Cells[m_FocusRow - 1][m_FocusCol].bLeftLineDn = 1;
4ed7fc 1642
ad1b4b 1643     }break;
Z 1644     case 2:
1645     {
1646         if (Cells[m_FocusRow - 1][m_FocusCol].nType == CMTerm1View::typeExt1)
1647         {
1648             //发送错误信息
1649             DbgLog(_T("删除纵线失败:光标位置错误!参数位置不允许删除纵线"));
1650             return;
1651         }
1652         //删除纵线时同步删除上一行
1653         Cells[m_FocusRow - 1][m_FocusCol].bLeftLineDn = 0;
4ed7fc 1654
ad1b4b 1655     }break;
Z 1656     default:
1657         break;
1658     }
4ed7fc 1659     //如果变化的是竖线,焦点不后移
Z 1660     if (!changeVLine)
1661     {
1662         //单元格位置后移
1663         m_FocusCol += 1;
1664     }
1665     
418cb3 1666     if (m_FocusCol >= 16) 
ad1b4b 1667     { 
Z 1668         m_FocusCol = 0;
1669         m_FocusRow += 1; 
1670     }
1671
418cb3 1672     this->RedrawWindow();
ad1b4b 1673     this->CellFocusChg(m_FocusRow, m_FocusCol);//改变焦点
418cb3 1674 }
Q 1675 void CMTerm1View::OnUpdateInsertBlankLine(CCmdUI *pCmdUI)
1676 {
1677     // TODO: 在此添加命令更新用户界面处理程序代码
1678 }
1679
1680 void CMTerm1View::OnDeleteBlankLine()
1681 {
1682     // TODO: 在此添加命令处理程序代码
1683     CString s1;
1684     s1.Format(_T("Delete Blank Line"));
1685     SysLog(s1);
1686 }
1687
1688 void CMTerm1View::OnUpdateDeleteBlankLine(CCmdUI *pCmdUI)
1689 {
1690     // TODO: 在此添加命令更新用户界面处理程序代码
1691 }
1692
1693 void CMTerm1View::OnRectSelect()
1694 {
1695     // TODO: 在此添加命令处理程序代码
1696 }
1697
1698
1699 void CMTerm1View::OnUpdateRectSelect(CCmdUI *pCmdUI)
1700 {
1701     // TODO: 在此添加命令更新用户界面处理程序代码
1702 }
1703
1704
1705 void CMTerm1View::OnTextFirst()
1706 {
1707     // TODO: 在此添加命令处理程序代码
1708 }
1709
1710
1711 void CMTerm1View::OnUpdateTextFirst(CCmdUI *pCmdUI)
1712 {
1713     // TODO: 在此添加命令更新用户界面处理程序代码
1714 }
1715
1716 void CMTerm1View::OnDisplayComments()
1717 {
1718     // TODO: 在此添加命令处理程序代码
1719     m_bShowComments = !m_bShowComments;
1720     int CellTotalHeight = m_CellHeight + (m_bShowComments ? m_CommentHeight : 0);
1721     CRect rect0;
1722     this->GetClientRect(&rect0);
1723
1724     CSize sizeTotal;
1725     // TODO: 计算此视图的合计大小
1726     sizeTotal.cx = m_LeftMargin + m_CellWidth * m_CellPerLine + m_CellWidth * 2;
1727     sizeTotal.cy = m_TopMargin + CellTotalHeight * (m_nTotalRow-1)  + rect0.Height();
1728     SetScrollSizes(MM_TEXT, sizeTotal);
1729     needReDraw = 1;
1730     this->Invalidate();
1731 }
1732
1733
1734 void CMTerm1View::OnUpdateDisplayComments(CCmdUI *pCmdUI)
1735 {
1736     // TODO: 在此添加命令更新用户界面处理程序代码
1737     pCmdUI->SetCheck(m_bShowComments == true);
1738 }
1739
1740
1741
1742 int CMTerm1View::UpdateStatusBar(int nIndex)
1743 {
1744     // TODO: 在此处添加实现代码.
1745     CString s1;
1746     CMTerm1Doc * pDoc = (CMTerm1Doc*)GetDocument();
1747
1748     if (nIndex == idxMachineType || nIndex == -1) {        //机型代码
1749         s1 = pDoc->m_sMachineType;
1750         m_pStatusBar->SetPaneText(idxMachineType,s1);
1751     }
1752     if (nIndex == idxProgPos || nIndex == -1) { //程序位置/步数
1753         s1.Format(_T("%5d/%5d"), m_nCurProgStep,pDoc->m_nProgSteps);
1754         m_pStatusBar->SetPaneText(idxProgPos, s1);
1755     }
1756     if (nIndex == idxOnline || nIndex == -1) { //在线 /离线
1757         if (!pDoc->m_bOnline) {
1758             s1 = _T("离线");
1759             m_pStatusBar->SetPaneText(idxOnline, s1);
1760             m_pStatusBar->SetPaneBackgroundColor(idxOnline);
1761         }
1762         else if (pDoc->m_bOnline) {
1763             if (pDoc->m_bSimulate)    {
1764                 s1 = _T("在线(仿真)");
1765                 m_pStatusBar->SetPaneText(2, s1);
1766                 m_pStatusBar->SetPaneBackgroundColor(idxOnline, OnlineColor);
1767             }else{
1768                 s1 = _T("在线");
1769                 m_pStatusBar->SetPaneText(2, s1);
1770                 m_pStatusBar->SetPaneBackgroundColor(idxOnline, OnlineColor);
1771             }
1772         }
1773     }
1774     if (nIndex == idxRunning || nIndex == -1) { // 运行 / 停止
1775         if (!pDoc->m_bOnline)        {
1776             s1 = _T("");
1777             m_pStatusBar->SetPaneText(idxRunning, s1);
1778             m_pStatusBar->SetPaneBackgroundColor(idxRunning);
1779             m_pStatusBar->SetPaneWidth(idxRunning, 0);
1780             m_pStatusBar->SetPaneStyle(idxRunning, SBPS_DISABLED);
1781
1782         }else if (!pDoc->m_bPlcRunning) {
1783             s1 = _T("PROG");
1784             m_pStatusBar->SetPaneText(idxRunning, s1);
1785             m_pStatusBar->SetPaneWidth(idxRunning, s1.GetLength()*8);
1786             m_pStatusBar->SetPaneBackgroundColor(idxRunning, ProgColor);
1787         }else {
1788             s1 = _T("RUN");
1789             m_pStatusBar->SetPaneText(idxRunning, s1);
1790             m_pStatusBar->SetPaneWidth(idxRunning, s1.GetLength() * 8);
1791             m_pStatusBar->SetPaneBackgroundColor(idxRunning, RunningColor);
1792         }
1793     }
1794     if (nIndex == idxMonitor || nIndex == -1) { // 监控 //
1795 //        s1 = pDoc->m_sMachineType;
1796         if (!m_bMonitoring) {
1797             s1 = _T("[监控停止]");
1798             m_pStatusBar->SetPaneText(idxMonitor, s1);
1799             m_pStatusBar->SetPaneBackgroundColor(idxMonitor);
1800         }else{
1801             s1 = _T("[正在监控]");
1802             m_pStatusBar->SetPaneText(idxMonitor, s1);
1803             m_pStatusBar->SetPaneBackgroundColor(idxMonitor, MonitorColor);
1804         }
1805     }
1806     if (nIndex == idxAddress || nIndex == -1) { // 地址,本站
1807 //        s1 = pDoc->m_sMachineType;
1808         if (!pDoc->m_bOnline) {
1809             s1 = _T("本站");
1810             m_pStatusBar->SetPaneText(idxAddress, s1);
1811             m_pStatusBar->SetPaneBackgroundColor(idxMonitor);
1812         }else {
1813             s1 = _T("本站");
1814             m_pStatusBar->SetPaneText(idxAddress, s1);
1815             m_pStatusBar->SetPaneBackgroundColor(idxMonitor, AddressColor);
1816         }
1817
1818     }
1819     if (nIndex == idxInfoDisp || nIndex == -1) { // INFO DISPLAY
1820 //        s1 = pDoc->m_sMachineType;
1821         m_pStatusBar->SetPaneText(idxInfoDisp, s1);
1822     }
1823
1824     return 0;
1825 }
1826
1827
1828 void CMTerm1View::OnUpdateIndicatorMonitorStatus(CCmdUI *pCmdUI)
1829 {
1830     // TODO: 在此添加命令更新用户界面处理程序代码
1831
1832     //pCmdUI->SetCheck(m_bMonitoring == true);
1833     if (!m_bMonitoring)     pCmdUI->SetText(_T("[监控停止]"));
1834     else     pCmdUI->SetText(_T("[正在监控]"));
1835 }
1836
1837 void CMTerm1View::OnUpdateIndicators(CCmdUI *pCmdUI)
1838 {
1839     // TODO: 在此添加命令更新用户界面处理程序代码
1840     CString s1;
1841     s1.Format(_T("pCmdUI nID %d "));
1842     DbgLog(s1);
1843     pCmdUI->m_nID;
1844     pCmdUI->SetText(_T("KL-D20N16"));
1845 }
1846
1847 void CMTerm1View::OnUpdateMachineType(CCmdUI *pCmdUI)
1848 {
1849     // TODO: 在此添加命令更新用户界面处理程序代码
1850     CString s1;
1851     s1.Format(_T("pCmdUI nID %d "));
1852     DbgLog(s1);
1853     pCmdUI->m_nID;
1854     pCmdUI->SetText(_T("KL-D20N16"));
1855 }
1856
1857 void CMTerm1View::OnUpdateProgramPos(CCmdUI *pCmdUI)
1858 {
1859     // TODO: 在此添加命令更新用户界面处理程序代码
1860     CString s1;
1861     s1.Format(_T("%5d/%5d"), 18, 55);
1862     pCmdUI->SetText(s1);
1863 }
1864
1865 void CMTerm1View::OnUpdateConnectivity(CCmdUI *pCmdUI)
1866 {
1867     // TODO: 在此添加命令更新用户界面处理程序代码
1868     CString s1;
1869     s1 = _T("离线");
1870     s1 = _T("在线");
1871
1872     pCmdUI->SetText(s1);
1873 }
1874 void CMTerm1View::OnUpdateRunStatus(CCmdUI *pCmdUI)
1875 {
1876     // TODO: 在此添加命令更新用户界面处理程序代码
1877     CString s1;
1878     CMTerm1Doc* pDoc = GetDocument();
1879     ASSERT_VALID(pDoc);
1880     if (!pDoc)    return;
1881     if (pDoc->m_bPlcRunning) {
1882         s1 = _T("运行");
1883         m_pStatusBar->SetPaneText(3, s1);
1884         m_pStatusBar->SetPaneTextColor(3, RGB(0, 0, 0));
1885     }
1886     else {
1887         s1 = _T("停止");
1888         m_pStatusBar->SetPaneText(3, s1);
1889         m_pStatusBar->SetPaneTextColor(3, RGB(0, 0, 0));
1890     }
1891     s1.Format(_T("PCmdUI %d %d"), pCmdUI->m_nID, pCmdUI->m_nIndex);
1892     DbgLog(s1);
1893
1894 //    pCmdUI->SetText(s1);
1895 }
1896 void CMTerm1View::OnUpdateMonitorStatus(CCmdUI *pCmdUI)
1897 {
1898     // TODO: 在此添加命令更新用户界面处理程序代码
1899     CString s1;
1900     s1 = _T("停止监控");
1901     s1 = _T("监控中");
1902     if (!m_bMonitoring)     pCmdUI->SetText(_T("[监控停止]"));
1903     else     pCmdUI->SetText(_T("[正在监控]"));
1904
1905 //    pCmdUI->SetText(s1);
1906 }
1907 void CMTerm1View::OnUpdateTargetAddress(CCmdUI *pCmdUI)
1908 {
1909     // TODO: 在此添加命令更新用户界面处理程序代码
1910     CString s1;
1911     s1 = _T("远程");
1912     s1 = _T("本站");
1913     pCmdUI->SetText(s1);
1914 }
1915
1916 void CMTerm1View::OnInputIoComment()
1917 {
1918     // TODO: 在此添加命令处理程序代码
1919     CString s1;
1920     int nRow, nCol;
1921     nRow = m_FocusRow;
1922     nCol = m_FocusCol;
1923     if (nCol < 0) { nCol = 0; }
1924     if (nCol >= m_CellPerLine) { nCol = m_CellPerLine - 1; }
1925
1926     CString sParam;
1927     sParam = Cells[nRow][nCol].sParam;
1928     int nDataType, nDataAddr, nStat;
1929     nDataType = Cells[nRow][nCol].nDataType;
1930     nDataAddr = Cells[nRow][nCol].nDataAddr;
1931     nStat = Cells[nRow][nCol].nStat;
1932
1933     s1.Format(_T("Name %s DataType %d DataAddr %d  Stat %d"),
1934         sParam, nDataType, nDataAddr, nStat);
1935     SysLog(s1);
1936     if (Cells[m_FocusRow][m_FocusCol].sParam == _T("")) {
1937         return;
1938     }
1939
1940     CMTerm1Doc * pDoc = GetDocument();
1941     CString sComment;
1942     pDoc->GetAnno(nDataType, nDataAddr, sComment);
1943     CDialogIoComment dialog1;
1944     dialog1.m_sIOName = sParam;
1945     dialog1.m_sComment = sComment;
1946     dialog1.m_nCoilType = nDataType;
1947     dialog1.m_nCoilAddr = nDataAddr;
1948     INT_PTR r = dialog1.DoModal();
1949     if (r == IDOK)
1950     {
1951         sComment = dialog1.m_sComment;
1952         pDoc->SetAnno(nDataType, nDataAddr, sParam, sComment);
1953         s1.Format(_T("Set %s %d %d  comment -> %s"), sParam, nDataType, nDataAddr, sComment);
1954         SysLog(s1);
1955         //needReDraw = 1;
1956         this->RedrawWindow();
1957     }
1958 }
1959
d34256 1960 /// <summary>
Z 1961 /// 程序数据转为梯形图
1962 /// </summary>
1963 /// <returns></returns>
418cb3 1964 int CMTerm1View::TransProgToLDS()
Q 1965 {
1966     CString s1;
1967     CMTerm1Doc * pDoc = (CMTerm1Doc*)GetDocument();
1968
1969     // 先扫描分开的程序段
1970     int stpos[100] = { 0 };
1971     int nSts = 0;
1972
ad1b4b 1973     for (int i = 0; i < m_nTotalRow && i < 2000; i++) 
Z 1974     {
1975         for (int j = 0; j < 16; j++) 
1976         {
418cb3 1977             Cells[i][j].clear();
aac3b3 1978              s1.Format(_T("%d:%d"), i, j);
418cb3 1979             Cells[i][j].sCoilName = s1;
Q 1980         }
1981     }
1982     POINT StPts[100];
1983     //    StPts[0] = POINT{ 0, 0 };
1984     POINT EndPt[100];
4ed7fc 1985
6ff05a 1986 //    POINT StrPt[100];
Q 1987 //    int nStrPts = 0;
418cb3 1988     int nEndPts = 0;
Q 1989     nSts = 0;
1990     int nCurLine = 0;
1991
1992     int cx = 0, cy = 0;
1993     int maxy = 0;
d34256 1994     try
418cb3 1995     {
d34256 1996         for (int i = 0; i < pDoc->m_nProgSteps; i++)
418cb3 1997         {
d34256 1998             int nOp = pDoc->Progs[i].nOpType1;
Z 1999             int nParamCount = pDoc->Progs[i].nParamCount;
2000             CStringA OpName;
2001             CStringA ShowTxt;
2002             pDoc->OpToTxt(nOp, OpName);
2003             pDoc->OpToShowTxt(nOp, ShowTxt);
2004             int nPairTo = pDoc->Progs[i].PairTo;
2005             int nPairOp = 0;
e55aec 2006             if (nPairTo)
Z 2007             {
2008                 nPairOp = pDoc->Progs[nPairTo].nOpType1;
2009             }
d34256 2010             int nCellType;
Z 2011             switch (nOp)
2012             {
2013             case OP_NOP:
2014                 break;
61deef 2015             case OP_END:
Q 2016                 nCellType =  typeEND;
2017                 nCurLine = cy;
2018                 cx = 0;
2019                 if (cx <= m_CellPerLine) {
2020
2021                     int hasData = 1;
2022                     while (hasData) {
2023                         hasData = 0;
2024                         for (int j = 0; j < m_CellPerLine; j++) {
2025                             if (Cells[nCurLine][j].nType != 0) {
2026                                 nCurLine++; hasData = 1; break;
2027                             }
2028                         }
2029                     }
2030                     cy = nCurLine;
2031                     for (int j = 0; j < m_CellPerLine; j++)
2032                     {
2033                         Cells[cy][j].nType = typeLine1;
2034                     }
2035                     Cells[cy][m_CellPerLine - 1].nType = nCellType;
2036                     Cells[cy][cx].nOpType = nOp;
2037                     Cells[cy][m_CellPerLine - 1].nProgStep = i;
2038                 }
2039                 if (cy > maxy) { maxy = cy; }
2040                 //cy++;
2041                 break;
2042                 break;
d34256 2043             case OP_ST:
Z 2044             case OP_ST_:
e55aec 2045                 if (i == 0) 
Z 2046                 {
418cb3 2047
d34256 2048                 }
e55aec 2049                 else 
Z 2050                 {
d34256 2051                     //记录当前位置 
Z 2052                     EndPt[nEndPts] = POINT{ cx,cy };
2053                     nEndPts++;
e55aec 2054                     if (nPairOp == OP_ANS) 
Z 2055                     {
d34256 2056                         //继续前进                
Z 2057                         //cx = 0, cy = nCurLine;
2058                         //cx = StPts[nSts - 1].x;
2059                         //nCurLine = cy + 1; //另起一行
e55aec 2060 ///*                
d34256 2061                         nCurLine = cy;
Z 2062                         int hasData = 1;
2063                         while (hasData) {
2064                             hasData = 0;
e55aec 2065                             for (int j = cx + 1; j < m_CellPerLine; j++) 
Z 2066                             {
2067                                 if (Cells[nCurLine][j].nType != 0) 
2068                                 {
d34256 2069                                     nCurLine++; hasData = 1; break;
Z 2070                                 }
418cb3 2071                             }
Q 2072                         }
e55aec 2073                         //nCurLine = maxy + 1; //另起一行
Z 2074                         if (nCurLine > maxy)
2075                         {
2076                             maxy = nCurLine;
2077                         }
2078                         for (int j = cy; j < nCurLine; j++) 
2079                         {
d34256 2080                             Cells[j][cx].bLeftLineDn = 1;
Z 2081                             Cells[j + 1][cx].bLeftLineUp = 1;
2082                         }
2083                         cy = nCurLine;
2084                         //*/
418cb3 2085                     }
e55aec 2086                     else if (nPairOp == OP_ORS) 
Z 2087                     {
d34256 2088                         cx = StPts[nSts - 1].x;
Z 2089                         nCurLine = cy + 1; //另起一行
2090                         int hasData = 1;
e55aec 2091                         while (hasData) 
Z 2092                         {
d34256 2093                             hasData = 0;
e55aec 2094                             for (int j = cx; j < m_CellPerLine; j++) 
Z 2095                             {
2096                                 if (Cells[nCurLine][j].nType != 0) 
2097                                 {
d34256 2098                                     nCurLine++; hasData = 1; break;
Z 2099                                 }
418cb3 2100                             }
Q 2101                         }
d34256 2102                         //                    nCurLine = maxy + 1; //另起一行
Z 2103                         if (nCurLine > maxy) maxy = nCurLine;
e55aec 2104                         for (int j = cy; j < nCurLine; j++) 
Z 2105                         {
d34256 2106                             Cells[j][cx].bLeftLineDn = 1;
Z 2107                             Cells[j + 1][cx].bLeftLineUp = 1;
2108                         }
2109                         cy = nCurLine;
418cb3 2110                     }
e55aec 2111                     else if (nPairOp == 0) 
Z 2112                     {
6ff05a 2113 //                        if (i > 0 && nOp == pDoc->Progs[i-1].nOpType1)//如果前面也是ST,那就不换行
Q 2114 //                        {
4ed7fc 2115
6ff05a 2116 //                        }
Q 2117 //                        else
2118 //                        {
4ed7fc 2119                             nCurLine = ++maxy;
Z 2120                             cx = 0;
2121                             cy = nCurLine;
6ff05a 2122 //                        }
418cb3 2123                     }
Q 2124                 }
d34256 2125                 stpos[nSts] = i;
Z 2126                 StPts[nSts] = POINT{ cx,cy };
2127                 nSts++;
2128                 Cells[cy][cx].nType = pDoc->Progs[i].nOpType1 == OP_ST ? typeNO : typeNC; //typeNC
6ff05a 2129                 Cells[cy][cx].nOpType = nOp;
d34256 2130                 Cells[cy][cx].nProgStep = i;
Z 2131                 Cells[cy][cx].sCoilName = pDoc->Progs[i].Params[0].sParamStr;
2132                 Cells[cy][cx].sParam = pDoc->Progs[i].Params[0].sParamStr;
2133                 Cells[cy][cx].nDataType = pDoc->Progs[i].Params[0].nParamType;
2134                 Cells[cy][cx].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2135                 cx++;    //移到下一格
2136                 break;
2137             case OP_ST_EQ:
2138             case OP_ST_NE:
2139             case OP_ST_LT:
2140             case OP_ST_GT:
2141             case OP_ST_LE:
2142             case OP_ST_GE:
2143                 if (i == 0) {
418cb3 2144
Q 2145                 }
d34256 2146                 else {
Z 2147                     //记录当前位置 
2148                     EndPt[nEndPts] = POINT{ cx,cy };
2149                     nEndPts++;
2150                     if (nPairOp == OP_ANS) {
2151                         //继续前进                
2152                         //cx = 0, cy = nCurLine;
2153                     }
2154                     else if (nPairOp == OP_ORS) {
2155                         cx = StPts[nSts - 1].x;
2156                         nCurLine = cy + 1; //另起一行
2157                         int hasData = 1;
2158                         while (hasData) {
2159                             hasData = 0;
2160                             for (int j = cx; j < m_CellPerLine; j++) {
2161                                 if (Cells[nCurLine][j].nType != 0) {
2162                                     nCurLine++; hasData = 1; break;
2163                                 }
418cb3 2164                             }
Q 2165                         }
d34256 2166                         //                    nCurLine = maxy + 1; //另起一行
Z 2167                         if (nCurLine > maxy) maxy = nCurLine;
2168                         for (int j = cy; j < nCurLine; j++) {
2169                             Cells[j][cx].bLeftLineDn = 1;
2170                             Cells[j + 1][cx].bLeftLineUp = 1;
418cb3 2171                         }
d34256 2172                         cy = nCurLine;
Z 2173                     }
2174                     else if (nPairOp == 0) {
2175                         nCurLine = maxy + 1; //另起一行
2176                         maxy = nCurLine;
2177                         cx = 0; cy = nCurLine;
418cb3 2178                     }
Q 2179                 }
d34256 2180                 stpos[nSts] = i;
Z 2181                 StPts[nSts] = POINT{ cx,cy };
2182                 nSts++;
2183                 Cells[cy][cx].nType = typeCMP;
6ff05a 2184                 Cells[cy][cx].nOpType = nOp;
d34256 2185                 Cells[cy][cx].nProgStep = i;
Z 2186                 Cells[cy][cx].sParam = OpName;
2187                 Cells[cy][cx].sCoilName = ShowTxt;
2188                 Cells[cy][cx + 1].nType = typeExt1;
2189                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2190                 Cells[cy][cx + 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2191                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2192                 Cells[cy][cx + 2].nType = typeExt1;
2193                 Cells[cy][cx + 2].sParam = pDoc->Progs[i].Params[1].sParamStr;
2194                 Cells[cy][cx + 2].nDataType = pDoc->Progs[i].Params[1].nParamType;
2195                 Cells[cy][cx + 2].nDataAddr = pDoc->Progs[i].Params[1].nParamAddr;
2196                 cx += 3;    //移到下3格
2197                 break;
418cb3 2198
d34256 2199             case OP_AN:
Z 2200             case OP_AN_:
418cb3 2201
d34256 2202                 Cells[cy][cx].nType = nOp == OP_AN ? typeNO : typeNC; //typeNC
6ff05a 2203                 Cells[cy][cx].nOpType = nOp;
418cb3 2204                 Cells[cy][cx].nProgStep = i;
Q 2205                 Cells[cy][cx].sParam = pDoc->Progs[i].Params[0].sParamStr;
2206                 Cells[cy][cx].sCoilName = pDoc->Progs[i].Params[0].sParamStr;
2207                 Cells[cy][cx].nDataType = pDoc->Progs[i].Params[0].nParamType;
2208                 Cells[cy][cx].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
d34256 2209                 cx++;
Z 2210                 break;
2211             case OP_AN_EQ:
2212             case OP_AN_NE:
2213             case OP_AN_LT:
2214             case OP_AN_GT:
2215             case OP_AN_LE:
2216             case OP_AN_GE:
2217                 Cells[cy][cx].nType = typeCMP;
6ff05a 2218                 Cells[cy][cx].nOpType = nOp;
d34256 2219                 Cells[cy][cx].nProgStep = i;
Z 2220                 Cells[cy][cx].sCoilName = ShowTxt;
2221                 Cells[cy][cx + 1].nType = typeExt1;
2222                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2223                 Cells[cy][cx + 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2224                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2225                 Cells[cy][cx + 2].nType = typeExt1;
2226                 Cells[cy][cx + 2].sParam = pDoc->Progs[i].Params[1].sParamStr;
2227                 Cells[cy][cx + 2].nDataType = pDoc->Progs[i].Params[1].nParamType;
2228                 Cells[cy][cx + 2].nDataAddr = pDoc->Progs[i].Params[1].nParamAddr;
2229                 cx += 3;
2230                 break;
2231
2232             case OP_OR:
2233             case OP_OR_:
2234                 EndPt[nEndPts] = POINT{ cx,cy };
aac3b3 2235                  nEndPts++;
d34256 2236                 cx = StPts[nSts - 1].x;
Z 2237                 nCurLine = cy + 1; //另起一行
2238                 {
2239                     int hasData = 1;
aac3b3 2240                     while (hasData) 
Z 2241                     {
2242                         hasData = 0;             
2243                         for (int j = cx; j < m_CellPerLine; j++) 
2244                         {
2245                             if (Cells[nCurLine][j].nType != 0) 
2246                             {
2247                                 nCurLine++; 
2248                                 hasData = 1; 
2249                                 break;
d34256 2250                             }
Z 2251                         }
2252                     }
2253                 }
aac3b3 2254                 if (nCurLine > maxy)
Z 2255                 {
2256                     maxy = nCurLine;
2257                 }
2258                 for (int j = cy; j < nCurLine; j++) 
2259                 {
d34256 2260                     Cells[j][cx].bLeftLineDn = 1;
Z 2261                     Cells[j + 1][cx].bLeftLineUp = 1;
2262                 }
2263                 cy = nCurLine;
aac3b3 2264                 StPts[nSts] = POINT{ cx,cy };//+++
d34256 2265                 Cells[cy][cx].nProgStep = i;
Z 2266                 Cells[cy][cx].nType = nOp == OP_OR ? typeNO : typeNC; //typeNC
6ff05a 2267                 Cells[cy][cx].nOpType = nOp;
d34256 2268                 Cells[cy][cx].sCoilName = pDoc->Progs[i].Params[0].sParamStr;
Z 2269                 Cells[cy][cx].sParam = pDoc->Progs[i].Params[0].sParamStr;
2270                 Cells[cy][cx].nDataType = pDoc->Progs[i].Params[0].nParamType;
2271                 Cells[cy][cx].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2272                 cx++;
6ff05a 2273                 if (cx <= EndPt[nEndPts - 1].x)
Q 2274                 {    //本行补齐
2275                     for (int j = cx; j < EndPt[nEndPts - 1].x; j++)
2276                     {
2277                         Cells[cy][j].nType = typeLine1;
2278                     }
2279                     cx = EndPt[nEndPts - 1].x;
2280                 }
2281                 else {
2282                     //前一行补齐
2283                     for (int j = EndPt[nEndPts - 1].x; j < cx; j++)
2284                     {
2285                         Cells[EndPt[nEndPts - 1].y][j].nType = typeLine1;
2286                     }
d34256 2287
6ff05a 2288                 }
d34256 2289                 //连接上下线
Z 2290                 for (int j = EndPt[nEndPts - 1].y; j < cy; j++)
2291                 {
2292                     Cells[j][cx].bLeftLineDn = 1;
2293                     Cells[j + 1][cx].bLeftLineUp = 1;
2294                 }
2295                 //光标位置, 前一结束点位置
2296                 cy = EndPt[nEndPts - 1].y;
aac3b3 2297
d34256 2298                 nEndPts--;
Z 2299
2300                 break;
2301             case OP_OR_EQ:
2302             case OP_OR_NE:
2303             case OP_OR_LT:
2304             case OP_OR_GT:
2305             case OP_OR_LE:
2306             case OP_OR_GE:
2307                 EndPt[nEndPts] = POINT{ cx,cy };
2308                 nEndPts++;
2309                 cx = StPts[nSts - 1].x;
2310                 nCurLine = cy + 1; //另起一行
2311                 {
2312                     int hasData = 1;
2313                     while (hasData) {
2314                         hasData = 0;
2315                         for (int j = cx; j < m_CellPerLine; j++) {
2316                             if (Cells[nCurLine][j].nType != 0) {
2317                                 nCurLine++; hasData = 1; break;
2318                             }
2319                         }
2320                     }
2321                 }
2322                 if (nCurLine > maxy)    maxy = nCurLine;
2323                 for (int j = cy; j < nCurLine; j++) {
2324                     Cells[j][cx].bLeftLineDn = 1;
2325                     Cells[j + 1][cx].bLeftLineUp = 1;
2326                 }
2327                 cy = nCurLine;
2328                 Cells[cy][cx].nType = typeCMP;
6ff05a 2329                 Cells[cy][cx].nOpType = nOp;
d34256 2330                 Cells[cy][cx].nProgStep = i;
Z 2331                 Cells[cy][cx].sCoilName = ShowTxt;
2332                 Cells[cy][cx + 1].nType = typeExt1;
2333                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2334                 Cells[cy][cx + 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2335                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2336                 Cells[cy][cx + 2].nType = typeExt1;
2337                 Cells[cy][cx + 2].sParam = pDoc->Progs[i].Params[1].sParamStr;
2338                 Cells[cy][cx + 2].nDataType = pDoc->Progs[i].Params[1].nParamType;
2339                 Cells[cy][cx + 2].nDataAddr = pDoc->Progs[i].Params[1].nParamAddr;
2340                 cx += 3;
2341                 if (cx < EndPt[nEndPts - 1].x)
2342                 {    //本行补齐
2343                     for (int j = cx; j < EndPt[nEndPts - 1].x; j++)
2344                     {
2345                         Cells[cy][j].nType = typeLine1;
2346                     }
2347                     cx = EndPt[nEndPts - 1].x;
2348                 }
2349                 else {
2350                     //前一行补齐
2351                     for (int j = EndPt[nEndPts - 1].x; j < cx; j++)
2352                     {
2353                         Cells[EndPt[nEndPts - 1].y][j].nType = typeLine1;
2354                     }
2355
2356                 }
2357                 //连接上下线
2358                 for (int j = EndPt[nEndPts - 1].y; j < cy; j++)
2359                 {
2360                     Cells[j][cx].bLeftLineDn = 1;
2361                     Cells[j + 1][cx].bLeftLineUp = 1;
2362                 }
2363                 //光标位置, 前一结束点位置
2364                 cy = EndPt[nEndPts - 1].y;
2365                 nEndPts--;
2366
2367                 break;
2368             case OP_NOT:
2369                 Cells[cy][cx].nType = typeNOT;
6ff05a 2370                 Cells[cy][cx].nOpType = nOp;
d34256 2371                 Cells[cy][cx].sCoilName = _T("NOT");
Z 2372
2373                 Cells[cy][cx].nProgStep = i;
2374                 cx++;
2375                 break;
2376             case OP_DF:
2377             case OP_DF_:
2378                 Cells[cy][cx].nType = nOp == OP_DF ? typeDF : typeDF_;
6ff05a 2379                 Cells[cy][cx].nOpType = nOp;
d34256 2380                 Cells[cy][cx].sCoilName = nOp == OP_DF ? _T("DF") : _T("DF/");
Z 2381
2382                 Cells[cy][cx].nProgStep = i;
2383                 cx++;
2384                 break;
2385             case OP_ANS:
6ff05a 2386                 /*
4ed7fc 2387                 //ANS说明是有环路,整行进行移动(向右)从后向前进行移动
Z 2388                 EndPt[nEndPts].y;
2389                 for (int i = EndPt[nEndPts-1].x ; i > 0; i--)
2390                 {
2391                     for (int j = EndPt[nEndPts].x; j >= 0; j--)
2392                     {
2393                         if (j > 0
2394                             && Cells[cy + 1][j-1].nType == typeNone 
2395                             || Cells[cy + 1][j - 1].nType == typeLine1 
2396                             || Cells[cy + 1][j - 1].nType == typeLine2)
2397                         {
2398                             continue;                        
2399                         }
2400
2401                         Cells[cy + 1][j] = Cells[cy + 1][j - 1];
2402                     }
2403                 }
2404
2405                 Cells[EndPt[nEndPts].y][EndPt[nEndPts-1].x].bLeftLineDn = 1;
2406                 Cells[EndPt[nEndPts].y+1][EndPt[nEndPts-1].x].bLeftLineUp = 1;
6ff05a 2407                 */
d34256 2408                 nSts--;
Z 2409                 nEndPts--;
2410
2411                 break;
2412             case OP_ORS:
6ff05a 2413                 // 当前序列与前面的序列合并。
Q 2414                 //当前序列的开始结束位置
2415                 //EndPt[nEndPts] = POINT{ cx,cy };
2416                 //nEndPts++;
2417                 //StPts[nSts - 1]; EndPt[nEndPts - 1];
2418                 //前一序列的开始结束位置
2419                 StPts[nSts - 1]; EndPt[nEndPts - 1];
4ed7fc 2420
e55aec 2421                 if (nEndPts <= 0)
d34256 2422                 {
e55aec 2423                     break;
d34256 2424                 }
e55aec 2425
4ed7fc 2426                 //判断二者长度
Z 2427                 if (cx < EndPt[nEndPts - 1].x)
2428                 {    
2429                     //本行补齐
2430                     for (int j = cx; j < EndPt[nEndPts - 1].x; j++)
2431                     {
2432                         Cells[cy][j].nType = typeLine1;
2433                     }
2434                     cx = EndPt[nEndPts - 1].x;
2435                 }
2436                 else 
2437                 {
2438                     //前一行补齐
2439                     for (int j = EndPt[nEndPts - 1].x; j < cx; j++)
2440                     {
6ff05a 2441                         //if (Cells[EndPt[nEndPts - 1].y][j].nType == typeNone)
4ed7fc 2442                         {
Z 2443                             Cells[EndPt[nEndPts - 1].y][j].nType = typeLine1;
2444                         }
2445                     }
2446                 }
2447                 //连接上下线
6ff05a 2448                 for (int j = EndPt[nEndPts - 1].y; j < cy; j++)
Q 2449                 {
2450                     Cells[j][cx].bLeftLineDn = 1;
2451                     Cells[j + 1][cx].bLeftLineUp = 1;
2452                 }
2453                 //Cells[cy][cx].bLeftLineUp = 1;
2454                 //Cells[cy-1][cx].bLeftLineDn = 1;
4ed7fc 2455
Z 2456                 //光标位置, 前一结束点位置
d34256 2457                 nSts--;
Z 2458                 nEndPts--;
4ed7fc 2459                 cy = EndPt[nEndPts].y;
61deef 2460             //    cx = EndPt[nEndPts].x;
d34256 2461                 break;
Z 2462             case OP_PSHS:
6ff05a 2463                 EndPt[nEndPts] = POINT{ cx,cy };
Q 2464                 nEndPts++;
2465 /*
4ed7fc 2466                 StrPt[nStrPts] = POINT{ EndPt[nEndPts].x,EndPt[nEndPts].y+1 };
Z 2467                 nStrPts++;
6ff05a 2468 */
d34256 2469                 break;
Z 2470             case OP_RDS:
2471                 cx = EndPt[nEndPts - 1].x;
2472                 for (int j = cx; j < m_CellPerLine; j++) {
2473                     if (Cells[cy][j].nType != 0)
2474                     {
2475                         cy++; j = cx - 1; //break;
2476                     }
2477                 }
2478                 for (int j = EndPt[nEndPts - 1].y; j < cy; j++)
2479                 {
2480                     Cells[j][cx].bLeftLineDn = 1;
2481                     Cells[j + 1][cx].bLeftLineUp = 1;
2482                 }
2483                 break;
2484             case OP_POPS:
6ff05a 2485                 cx = EndPt[nEndPts - 1].x;
Q 2486                 for (int j = cx; j < m_CellPerLine; j++) {
2487                     if (Cells[cy][j].nType != 0)
2488                     {
2489                         cy++; j = cx - 1; break;
2490                     }
2491                 }
2492                 for (int j = EndPt[nEndPts - 1].y; j < cy; j++)
2493                 {
2494                     Cells[j][cx].bLeftLineDn = 1;
2495                     Cells[j + 1][cx].bLeftLineUp = 1;
2496                 }
2497                 nEndPts--;
2498 /*
4ed7fc 2499                 nStrPts--;
Z 2500                 cy = StrPt[nStrPts].y;
2501                 cx = StrPt[nStrPts].x;
6ff05a 2502 */
d34256 2503                 break;
Z 2504             case OP_OUT:
2505             case OP_SET:
2506             case OP_RESET:
2507                 nCellType = nOp == OP_OUT ? typeOUT : nOp == OP_SET ? typeSET : typeRESET;
2508                 nCurLine = cy;
2509                 if (cx <= m_CellPerLine) {
2510
2511                     int hasData = 1;
2512                     while (hasData) {
2513                         hasData = 0;
2514                         for (int j = cx; j < m_CellPerLine; j++) {
2515                             if (Cells[nCurLine][j].nType != 0) {
2516                                 nCurLine++; hasData = 1; break;
2517                             }
2518                         }
2519                     }
2520                     //if (nCurLine > maxy)    maxy = nCurLine;
2521                     for (int j = cy; j < nCurLine; j++) {
2522                         Cells[j][cx].bLeftLineDn = 1;
2523                         Cells[j + 1][cx].bLeftLineUp = 1;
2524                     }
2525                     cy = nCurLine;
2526                     for (int j = cx; j < m_CellPerLine; j++)
2527                     {
2528                         Cells[cy][j].nType = typeLine1;
2529                     }
2530                     Cells[cy][m_CellPerLine - 1].nType = nCellType;
6ff05a 2531                     Cells[cy][cx].nOpType = nOp;
d34256 2532                     Cells[cy][m_CellPerLine - 1].nProgStep = i;
Z 2533                     Cells[cy][m_CellPerLine - 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2534                     Cells[cy][m_CellPerLine - 1].sCoilName = pDoc->Progs[i].Params[0].sParamStr;
2535                     Cells[cy][m_CellPerLine - 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2536                     Cells[cy][m_CellPerLine - 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2537
2538                 }
2539                 else {
2540                     Cells[cy][cx].nType = nCellType;
6ff05a 2541                     Cells[cy][cx].nOpType = nOp;
d34256 2542                     Cells[cy][cx].nProgStep = i;
Z 2543                     Cells[cy][cx].sParam = pDoc->Progs[i].Params[0].sParamStr;
2544                     Cells[cy][cx].sCoilName = pDoc->Progs[i].Params[0].sParamStr;
2545                     Cells[cy][cx].nDataType = pDoc->Progs[i].Params[0].nParamType;
2546                     Cells[cy][cx].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2547                 }
2548                 if (cy > maxy) { maxy = cy; }
2549                 //cy++;
2550                 break;
2551
2552             case OP_TML:
2553             case OP_TMR:
2554             case OP_TMX:
2555             case OP_TMY:
61deef 2556                 nCurLine = cy;
Q 2557                 {
2558                     int hasData = 1;
2559                     while (hasData) {
2560                         hasData = 0;
2561                         for (int j = cx; j < m_CellPerLine; j++) {
2562                             if (Cells[nCurLine][j].nType != 0) {
2563                                 nCurLine++; hasData = 1; break;
2564                             }
2565                         }
2566                     }
2567                     //if (nCurLine > maxy)    maxy = nCurLine;
2568                     for (int j = cy; j < nCurLine; j++) {
2569                         Cells[j][cx].bLeftLineDn = 1;
2570                         Cells[j + 1][cx].bLeftLineUp = 1;
2571                     }
2572                 }
2573                 cy = nCurLine;
d34256 2574                 Cells[cy][cx].nType = typeTM;
6ff05a 2575                 Cells[cy][cx].nOpType = nOp;
d34256 2576                 Cells[cy][cx].nProgStep = i;
Z 2577                 Cells[cy][cx].sCoilName = ShowTxt;
2578                 Cells[cy][cx + 1].nType = typeExt1;
2579                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2580                 Cells[cy][cx + 1].nDataType = KLDataTypeEV;
2581                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2582                 Cells[cy][cx + 2].nType = typeExt1;
2583                 Cells[cy][cx + 2].sParam = pDoc->Progs[i].Params[1].sParamStr;
2584                 Cells[cy][cx + 2].nDataType = pDoc->Progs[i].Params[1].nParamType;
2585                 Cells[cy][cx + 2].nDataAddr = pDoc->Progs[i].Params[1].nParamAddr;
2586                 cx += 3;
2587                 break;
2588             case OP_INC:
2589             case OP_DEC:
2590                 Cells[cy][cx].nType = typeFN1;
6ff05a 2591                 Cells[cy][cx].nOpType = nOp;
d34256 2592                 Cells[cy][cx].nProgStep = i;
Z 2593                 Cells[cy][cx].sCoilName = ShowTxt;
2594                 Cells[cy][cx + 1].nType = typeExt1;
2595                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2596                 Cells[cy][cx + 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2597                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2598                 cx += 2;
2599                 break;
2600
2601             case OP_MV:
2602             case OP_ADD2:
2603             case OP_SUB2:
2604                 Cells[cy][cx].nType = typeFN2;
6ff05a 2605                 Cells[cy][cx].nOpType = nOp;
d34256 2606                 Cells[cy][cx].nProgStep = i;
Z 2607                 Cells[cy][cx].sCoilName = ShowTxt;
2608                 Cells[cy][cx + 1].nType = typeExt1;
2609                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2610                 Cells[cy][cx + 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2611                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2612                 Cells[cy][cx + 2].nType = typeExt1;
2613                 Cells[cy][cx + 2].sParam = pDoc->Progs[i].Params[1].sParamStr;
2614                 Cells[cy][cx + 2].nDataType = pDoc->Progs[i].Params[1].nParamType;
2615                 Cells[cy][cx + 2].nDataAddr = pDoc->Progs[i].Params[1].nParamAddr;
2616                 cx += 3;
2617                 break;
2618
2619             case OP_ADD3:
2620             case OP_SUB3:
2621             case OP_MUL:
2622             case OP_DIV:
2623                 Cells[cy][cx].nType = typeFN3;
6ff05a 2624                 Cells[cy][cx].nOpType = nOp;
d34256 2625                 Cells[cy][cx].nProgStep = i;
Z 2626                 Cells[cy][cx].sCoilName = ShowTxt;
2627                 Cells[cy][cx + 1].nType = typeExt1;
2628                 Cells[cy][cx + 1].sParam = pDoc->Progs[i].Params[0].sParamStr;
2629                 Cells[cy][cx + 1].nDataType = pDoc->Progs[i].Params[0].nParamType;
2630                 Cells[cy][cx + 1].nDataAddr = pDoc->Progs[i].Params[0].nParamAddr;
2631                 Cells[cy][cx + 2].nType = typeExt1;
2632                 Cells[cy][cx + 2].sParam = pDoc->Progs[i].Params[1].sParamStr;
2633                 Cells[cy][cx + 2].nDataType = pDoc->Progs[i].Params[1].nParamType;
2634                 Cells[cy][cx + 2].nDataAddr = pDoc->Progs[i].Params[1].nParamAddr;
2635                 Cells[cy][cx + 3].nType = typeExt1;
2636                 Cells[cy][cx + 3].sParam = pDoc->Progs[i].Params[2].sParamStr;
2637                 Cells[cy][cx + 3].nDataType = pDoc->Progs[i].Params[2].nParamType;
2638                 Cells[cy][cx + 3].nDataAddr = pDoc->Progs[i].Params[2].nParamAddr;
2639                 cx += 4;
2640                 break;
2641
2642             default:
2643                 break;
418cb3 2644             }
6ff05a 2645             if (cy > maxy) { maxy = cy; }
418cb3 2646         }
Q 2647     }
d34256 2648     catch (const std::exception&)
Z 2649     {
2650         DbgLog(_T("无法绘制图形(程序不合理)"));
2651     }
2652
418cb3 2653     m_nTotalRow = maxy + 1;
Q 2654     /*
2655         for (int i = 0; i < 25; i++)
2656         {
2657             for (int j = 0; j < 16; j++)
2658             {
2659                 Cells[i][j].nType = i;
2660                 s1.Format(_T("%d:%d"), i, j);
2661                 Cells[i][j].sCoilName = s1;
2662             }
2663         }
2664     */
2665     needReDraw = 1;
6ff05a 2666     return 0;
Q 2667 }
2668
2669
2670 int CMTerm1View::AddNode(int nType, int CellX, int CellY, CString sCoilName, int PrevNode)
2671 {
2672     node& theNode = nodes[nNodeCount];
2673
2674     theNode.nId = nNodeCount;
2675
2676     theNode.bEnable = 1;
2677     theNode.nType = nType;
2678     theNode.indegree = 0;
2679     theNode.outdegree = 0;
2680     theNode.firstOut = 0;
2681     theNode.firstIn = 0;
2682     theNode.input = 0;
2683     theNode.result = 0;
2684     theNode.nCellX = CellX;
2685     theNode.nCellY = CellY;
2686     theNode.CoilName = sCoilName;
2687     theNode.InProcCount = 0;
2688     theNode.OutProcCount = 0;
2689     theNode.OutProcAllDone = 0;
2690     theNode.prog1.Progs.clear();
2691     int nOp = Cells[CellY][CellX].nOpType;
2692     int nCoilType, nCoilAddr;
2693     if (nType == typeNO)
2694      {
2695         CMTerm1Doc::stProg prog0;
61deef 2696         if (CellX == 0) {
6ff05a 2697             prog0.nOpType1 = OP_ST; // OP_AN;
61deef 2698         }else 
Q 2699         if (nOp >= 1 && nOp <= 255) {
2700             //prog0.nOpType1 = nOp; // OP_AN;
2701             prog0.nOpType1 = OP_AN; // OP_AN;
6ff05a 2702         }
Q 2703         else {
2704             prog0.nOpType1 = OP_AN; // OP_AN;
2705         }
2706         prog0.nParamCount = 1;
2707         prog0.Params[0].sParamStr = sCoilName;
2708         CStringA s2A;
2709         s2A = sCoilName;
2710         GetDocument()->TxtToCoilType(s2A,&nCoilType,&nCoilAddr);
2711
2712         prog0.Params[0].nParamType = nCoilType;
2713         prog0.Params[0].nParamAddr = nCoilAddr;
2714         theNode.prog1.Append(prog0);
2715     }
2716     else if (nType == typeNC) {
2717         CMTerm1Doc::stProg prog0;
61deef 2718         if (CellX == 0) {
6ff05a 2719             prog0.nOpType1 = OP_ST_; // OP_AN;
Q 2720         }
61deef 2721         else if (nOp >= 1 && nOp <= 255) {
Q 2722             //prog0.nOpType1 = nOp; // OP_AN;
2723             prog0.nOpType1 = OP_AN_; // OP_AN;
2724         }
2725         else  {
6ff05a 2726             prog0.nOpType1 = OP_AN_; // OP_AN;
Q 2727         }
2728         prog0.nParamCount = 1;
2729         prog0.Params[0].sParamStr = Cells[CellY][CellX].sCoilName;
2730         CStringA s2A;
2731         s2A = sCoilName;
2732         GetDocument()->TxtToCoilType(s2A, &nCoilType, &nCoilAddr);
2733
2734         prog0.Params[0].nParamType = nCoilType;
2735         prog0.Params[0].nParamAddr = nCoilAddr;
2736         theNode.prog1.Append(prog0);
61deef 2737     }
Q 2738     else if (nType == typeEND) {
2739         theNode.prog1.Append(CMTerm1Doc::stProg(OP_END));
6ff05a 2740     }
Q 2741     else if (nType == typePP) {
2742         CMTerm1Doc::stProg prog0;
2743         prog0.nOpType1 = Cells[CellY][CellX].nOpType;
2744         prog0.nParamCount = 1;
2745         prog0.Params[0].sParamStr = sCoilName;
2746         prog0.Params[0].nParamType = Cells[CellY][CellX].nDataType;
2747         prog0.Params[0].nParamAddr = Cells[CellY][CellX].nDataAddr;
2748         theNode.prog1.Append(prog0);
2749     }
2750     else if (nType == typePN) {
2751         CMTerm1Doc::stProg prog0;
2752         prog0.nOpType1 = Cells[CellY][CellX].nOpType;
2753         prog0.nParamCount = 1;
2754         prog0.Params[0].sParamStr = sCoilName;
2755         prog0.Params[0].nParamType = Cells[CellY][CellX].nDataType;
2756         prog0.Params[0].nParamAddr = Cells[CellY][CellX].nDataAddr;
2757         theNode.prog1.Append(prog0);
2758     }
2759     else if (nType == typeNOT) {
2760         theNode.prog1.Append(CMTerm1Doc::stProg(OP_NOT));
2761     }
2762     else if (nType == typeDF) {
2763         theNode.prog1.Append(CMTerm1Doc::stProg(OP_DF));
2764     }
2765     else if (nType == typeDF_) {
2766         theNode.prog1.Append(CMTerm1Doc::stProg(OP_DF_));
2767     }
2768     else if (nType == typeOUT) {
2769         CMTerm1Doc::stProg prog0;
2770         prog0.nOpType1 = OP_OUT;
2771         prog0.nParamCount = 1;
2772         prog0.Params[0].sParamStr = sCoilName;
2773         CStringA s2A;
2774         s2A = sCoilName;
2775         GetDocument()->TxtToCoilType(s2A, &nCoilType, &nCoilAddr);
2776
2777         prog0.Params[0].nParamType = nCoilType;
2778         prog0.Params[0].nParamAddr = nCoilAddr;
2779         theNode.prog1.Append(prog0);
2780     }
2781     else if (nType == typeSET) {
2782         CMTerm1Doc::stProg prog0;
2783         prog0.nOpType1 = OP_SET;
2784         prog0.nParamCount = 1;
2785         prog0.Params[0].sParamStr = sCoilName;
2786         CStringA s2A;
2787         s2A = sCoilName;
2788         GetDocument()->TxtToCoilType(s2A, &nCoilType, &nCoilAddr);
2789
2790         prog0.Params[0].nParamType = nCoilType;
2791         prog0.Params[0].nParamAddr = nCoilAddr;
2792         theNode.prog1.Append(prog0);
2793     }
2794     else if (nType == typeRESET) {
2795         CMTerm1Doc::stProg prog0;
2796         prog0.nOpType1 = OP_RESET;
2797         prog0.nParamCount = 1;
2798         prog0.Params[0].sParamStr = sCoilName;
2799         CStringA s2A;
2800         s2A = sCoilName;
2801         GetDocument()->TxtToCoilType(s2A, &nCoilType, &nCoilAddr);
2802
2803         prog0.Params[0].nParamType = nCoilType;
2804         prog0.Params[0].nParamAddr = nCoilAddr;
2805         theNode.prog1.Append(prog0);
2806     }
2807     else if (nType == typeCMP) {
2808         CMTerm1Doc::stProg prog0;
2809         Cells[CellY][CellX];
2810         prog0.nOpType1 = Cells[CellY][CellX].nOpType;
2811         prog0.nParamCount = 2;
2812         prog0.Params[0].sParamStr = Cells[CellY][CellX + 1].sParam;
2813         prog0.Params[0].nParamType = Cells[CellY][CellX + 1].nDataType;
2814         prog0.Params[0].nParamAddr = Cells[CellY][CellX + 1].nDataAddr;
2815         prog0.Params[1].sParamStr = Cells[CellY][CellX + 2].sParam;
2816         prog0.Params[1].nParamType = Cells[CellY][CellX + 2].nDataType;
2817         prog0.Params[1].nParamAddr = Cells[CellY][CellX + 2].nDataAddr;
2818         theNode.prog1.Append(prog0);
2819     }
2820     else if (nType == typeTM) {
2821         CMTerm1Doc::stProg prog0;
2822         prog0.nOpType1 = Cells[CellY][CellX].nOpType;
2823         prog0.nParamCount = 2;
2824         prog0.Params[0].sParamStr = Cells[CellY][CellX + 1].sParam;
2825         prog0.Params[0].nParamType = Cells[CellY][CellX + 1].nDataType;
2826         prog0.Params[0].nParamAddr = Cells[CellY][CellX + 1].nDataAddr;
2827
2828         prog0.Params[1].sParamStr = Cells[CellY][CellX + 2].sParam;
2829         prog0.Params[1].nParamType = Cells[CellY][CellX + 2].nDataType;
2830         prog0.Params[1].nParamAddr = Cells[CellY][CellX + 2].nDataAddr;
2831
2832         theNode.prog1.Append(prog0);
2833     }
2834     else if (nType == typeFN1) {
2835         CMTerm1Doc::stProg prog0;
2836         prog0.nOpType1 = Cells[CellY][CellX].nOpType;;
2837         prog0.nParamCount = 1;
2838         prog0.Params[0].sParamStr = Cells[CellY][CellX + 1].sParam;
2839         prog0.Params[0].nParamType = Cells[CellY][CellX + 1].nDataType;
2840         prog0.Params[0].nParamAddr = Cells[CellY][CellX + 1].nDataAddr;
2841         theNode.prog1.Append(prog0);
2842     }
2843     else if (nType == typeFN2) {
2844         CMTerm1Doc::stProg prog0;
2845         prog0.nOpType1 = Cells[CellY][CellX].nOpType;;
2846         prog0.nParamCount = 2;
2847         prog0.Params[0].sParamStr = Cells[CellY][CellX + 1].sParam;
2848         prog0.Params[0].nParamType = Cells[CellY][CellX + 1].nDataType;
2849         prog0.Params[0].nParamAddr = Cells[CellY][CellX + 1].nDataAddr;
2850         prog0.Params[1].sParamStr = Cells[CellY][CellX + 2].sParam;
2851         prog0.Params[1].nParamType = Cells[CellY][CellX + 2].nDataType;
2852         prog0.Params[1].nParamAddr = Cells[CellY][CellX + 2].nDataAddr;
2853         theNode.prog1.Append(prog0);
2854     }
2855     else if (nType == typeFN3) {
2856         CMTerm1Doc::stProg prog0;
2857         prog0.nOpType1 = Cells[CellY][CellX].nOpType;;
2858         prog0.nParamCount = 3;
2859         prog0.Params[0].sParamStr = Cells[CellY][CellX + 1].sParam;
2860         prog0.Params[0].nParamType = Cells[CellY][CellX + 1].nDataType;
2861         prog0.Params[0].nParamAddr = Cells[CellY][CellX + 1].nDataAddr;
2862         prog0.Params[1].sParamStr = Cells[CellY][CellX + 2].sParam;
2863         prog0.Params[1].nParamType = Cells[CellY][CellX + 2].nDataType;
2864         prog0.Params[1].nParamAddr = Cells[CellY][CellX + 2].nDataAddr;
2865         prog0.Params[2].sParamStr = Cells[CellY][CellX + 3].sParam;
2866         prog0.Params[2].nParamType = Cells[CellY][CellX + 3].nDataType;
2867         prog0.Params[2].nParamAddr = Cells[CellY][CellX + 3].nDataAddr;
2868
2869         theNode.prog1.Append(prog0);
2870     }
2871     else if (nType == typeFN4) {
2872         CMTerm1Doc::stProg prog0;
2873         prog0.nOpType1 = Cells[CellY][CellX].nOpType;;
2874         prog0.nParamCount = 4;
2875         prog0.Params[0].sParamStr = Cells[CellY][CellX + 1].sParam;
2876         prog0.Params[0].nParamType = Cells[CellY][CellX + 1].nDataType;
2877         prog0.Params[0].nParamAddr = Cells[CellY][CellX + 1].nDataAddr;
2878         prog0.Params[1].sParamStr = Cells[CellY][CellX + 2].sParam;
2879         prog0.Params[1].nParamType = Cells[CellY][CellX + 2].nDataType;
2880         prog0.Params[1].nParamAddr = Cells[CellY][CellX + 2].nDataAddr;
2881         prog0.Params[2].sParamStr = Cells[CellY][CellX + 3].sParam;
2882         prog0.Params[2].nParamType = Cells[CellY][CellX + 3].nDataType;
2883         prog0.Params[2].nParamAddr = Cells[CellY][CellX + 3].nDataAddr;
2884         prog0.Params[3].sParamStr = Cells[CellY][CellX + 4].sParam;
2885         prog0.Params[3].nParamType = Cells[CellY][CellX + 4].nDataType;
2886         prog0.Params[3].nParamAddr = Cells[CellY][CellX + 4].nDataAddr;
2887         theNode.prog1.Append(prog0);
2888     }
2889     if (PrevNode > 0) {
2890         AddArc(PrevNode, nNodeCount);
2891     }
2892     nNodeCount++;
2893     return nNodeCount-1;
2894 }
2895
2896 int SearchLastInArc(int nNodeID)
2897 {
2898     int ArcId = 0;
2899
2900     return ArcId;
2901 }
2902
2903 int SearchLastOutArc(int nNodeID)
2904 {
2905         int ArcId = 0;
2906
2907         return ArcId;
2908 }
2909
2910 int CMTerm1View::AddArc(int nNodeID1, int nNodeID2)
2911 {
2912     node& theNode1 = nodes[nNodeID1];
2913     node& theNode2 = nodes[nNodeID2];
2914
2915     arc& theArc = arcs[nArcCount];
2916     theArc.nId = nArcCount;
2917     theArc.bEnable = 1;
2918     theNode2.firstIn;
2919
2920
2921     theArc.headNode = nNodeID2;
2922     theArc.tailNode = nNodeID1;
2923     theArc.hlinkId = 0;
2924     theArc.tlinkId = 0;
2925
2926     theArc.tailvex = &theNode1;
2927     theArc.headvex = &theNode2;
2928     theArc.tlink = 0;
2929     theArc.hlink = 0;
2930
2931     theNode1.outdegree++;
2932     theNode2.indegree++;
2933
2934     //如果顶点已经有 连接 ,将新的弧加到已有弧的后面。
2935
2936     if (theNode1.firstOut == 0) {
2937         theNode1.firstOut = &theArc; 
2938     }else {
2939         arc * p1 = theNode1.firstOut;
2940         for (; p1->tlink != 0;) {
2941              p1 = p1->tlink;
2942         }
2943         p1->tlink = &theArc;
2944         p1->tlinkId = nArcCount;
2945     }
2946
2947     if (theNode2.firstIn == 0) {
2948         theNode2.firstIn = &theArc;
2949     }else{
2950         arc* p1 = theNode2.firstIn;
2951         for (; p1->hlink != 0;) {
2952             p1 = p1->hlink;
2953         }
2954         p1->hlink = &theArc;
2955         p1->hlinkId = nArcCount;
2956     }
2957
2958     nArcCount++;
2959     return nArcCount;
2960 }
2961
2962 int CMTerm1View::MergeParallelNodeWithinVP(int nVPNodeId1, int nVPNodeId2)        //合并两个串联的虚节点之间所有的并行 Node,并行数量可能大于2个。
2963 {
2964     node& theNode1 = nodes[nVPNodeId1];            //虚节点1
2965     node& theNode2 = nodes[nVPNodeId2];            //虚节点2
2966     // 必须前者 与 后者 之间有两条以上 且连续,其中一方为另一方的子集 才能合并。
2967     // 先找到两者连接的弧
2968     if (!theNode1.bEnable || !theNode2.bEnable) return -1;
2969     if (theNode1.outdegree < 2 || theNode2.indegree < 2 ) return -2;
2970 //    if (theNode1.firstOut != theNode2.firstIn) return -3;
2971 // 
2972 //  先找到第一个连接
2973 // 
2974     CString s1;
2975     //先判断两者大小
2976     int n1 = theNode1.outdegree;
2977     int n2 = theNode2.indegree;
2978
2979     if (n1 <= n2) {            //前者是后的的子集
2980         int n = 0;
2981         arc* ptheArc1 = theNode1.firstOut;
2982         while (ptheArc1)
2983         {    // 取得连接的实节点地址;
2984             node* pThisNode1 = ptheArc1->headvex;
2985             // 取得实节点连接的弧;
2986             arc* ptheArc2 = pThisNode1->firstOut;
2987             // 取出弧连接的下一个节点, 目标虚节点
2988             node* pThatNode1 = ptheArc2->headvex;
2989             // 判断这个点是不是指定的虚节点
2990             if (pThatNode1 != &theNode2) { return -3; } // 没连接到第二个虚节点
2991             n++;
2992             // 继续下一个连接的弧;
2993             ptheArc1 = ptheArc1->tlink;
2994         }
2995         if (theNode1.outdegree != n ) return -2;
2996
2997         //node& theNode;
2998         // 第二次,重来一遍,开始合并程序 
2999
3000         stProgSection prog2;
3001         ptheArc1 = theNode1.firstOut;
3002         node* pThisNode1 = ptheArc1->headvex;    // 第一个实节点
3003         stProgSection prog1 = pThisNode1->prog1;
3004         if (prog1.Progs[0].nOpType1 == OP_AN) { prog1.Progs[0].nOpType1 = OP_ST; }
61deef 3005         else if (prog1.Progs[0].nOpType1 == OP_AN_) { prog1.Progs[0].nOpType1 = OP_ST_; }
Q 3006         else if (prog1.Progs[0].nOpType1 == OP_ST || prog1.Progs[0].nOpType1 == OP_ST_ ){
3007             prog1.Prefix += 1;
3008             s1.Format(_T(" <+1  %s"),prog1.ToText());    DbgLog(s1);
3009         }
3010         else {
3011             prog1.Prefix += 0;
3012             s1.Format(_T(" < +0 %s"),prog1.ToText());    DbgLog(s1);
3013         }
6ff05a 3014         prog2 = prog1;                // 取得第一个实节点的程序
Q 3015         ptheArc1 = ptheArc1->tlink;                //下一个弧
3016         while (ptheArc1)
3017         {
3018             //取得相连的实节点地址
3019             node* pThisNode2 = ptheArc1->headvex;
3020             stProgSection prog1 = pThisNode2->prog1;
3021             if (prog1.Progs[0].nOpType1 == OP_AN) { prog1.Progs[0].nOpType1 = OP_ST; }
61deef 3022             else if (prog1.Progs[0].nOpType1 == OP_AN_) { prog1.Progs[0].nOpType1 = OP_ST_; }
Q 3023             else if (prog1.Progs[0].nOpType1 == OP_ST || prog1.Progs[0].nOpType1 == OP_ST_) {
3024                 prog1.Prefix += 1;
3025                 s1.Format(_T(" < 2 +1 %s"), prog1.ToText());    DbgLog(s1);
3026                 if (theNode1.nType == -1) { prog1.reduce(); }
3027             }
3028             else {
3029                 prog1.Prefix += 0;
3030                 s1.Format(_T(" < 2 +0 %s"),prog1.ToText());    DbgLog(s1);
3031             }
3032
6ff05a 3033             if (prog1.Progs.size() > 1) {
Q 3034                 prog1.Append(CMTerm1Doc::stProg(OP_ORS));
3035             }
3036             else {
3037                 if (pThisNode2->nType == typeNC) prog1.Progs[0].nOpType1 = OP_OR_;
3038                 else if (pThisNode2->nType == typeNO) prog1.Progs[0].nOpType1 = OP_OR;
3039                 else prog1.Progs[0].nOpType1 = OP_OR;
3040             }
3041             prog2 += prog1;
3042
3043             // 取得实节点连接的弧;
3044
3045             arc* ptheArc2 = pThisNode2->firstOut;
3046             RemoveArc(ptheArc2->nId);                //删除弧
3047             arc* pTheNextArc = ptheArc1->tlink;        //取得下一个弧并保存
3048             RemoveArc(ptheArc1->nId);                //删除当前弧
3049             pThisNode2->bEnable = 0;                //删除实节点
3050             ptheArc1 = pTheNextArc;
3051         }
3052         if (theNode1.nType == -1 && theNode2.nType == -1) { prog2.Append(CMTerm1Doc::stProg(OP_ANS)); }
3053         pThisNode1->prog1 = prog2;                //将所有程序汇总到第一个实节点
61deef 3054     //    pThisNode1->prog1.reduce();
6ff05a 3055     //    s1 = prog2.ToText(GetDocument());
Q 3056     //    DbgLog(_T("------ ") + s1);
3057     }
3058     else {            // n1> n2  // 后者是前者的子集
3059         int n = 0;
3060         arc* ptheArc1 = theNode2.firstIn;
3061         while (ptheArc1)
3062         {
3063
3064             //取得相连的虚节点地址
3065
3066             // 取得连接的实节点地址;
3067             node* pThisNode1 = ptheArc1->tailvex;
3068             // 取得实节点连接的弧;
3069             arc* ptheArc2 = pThisNode1->firstIn;
3070             // 取出弧连接的下一个节点
3071             node* pThatNode1 = ptheArc2->tailvex;
3072             // 判断这个点是不是指定的虚节点
3073             if (pThatNode1 != &theNode1) { return -3; } // 没连接到第二个虚节点
3074             n++;
3075             // 继续下一个连接的弧;
3076             ptheArc1 = ptheArc1->hlink;
3077         }
3078         if (theNode2.indegree != n) return -1;
3079         //node& theNode;
3080         // 第二次,重来一遍,开始合并程序 
3081         stProgSection prog2;
3082         ptheArc1 = theNode2.firstIn;
3083         node* pThisNode1 = ptheArc1->tailvex;    // 第一个实节点
3084         stProgSection prog1 = pThisNode1->prog1;
3085         if (prog1.Progs[0].nOpType1 == OP_AN) { prog1.Progs[0].nOpType1 = OP_ST; }
61deef 3086         else if (prog1.Progs[0].nOpType1 == OP_AN_) { prog1.Progs[0].nOpType1 = OP_ST_; }
Q 3087         else if (prog1.Progs[0].nOpType1 == OP_ST || prog1.Progs[0].nOpType1 == OP_ST_) {
3088             prog1.Prefix += 1;
3089             s1.Format(_T(" > +1 %s"),prog1.ToText());    DbgLog(s1);
3090         }
3091         else {
3092             prog1.Prefix += 0;
3093             s1.Format(_T(" > +0 %s"), prog1.ToText());    DbgLog(s1);
3094         }
6ff05a 3095         prog2 = prog1;                // 取得第一个实节点的程序
Q 3096
3097         ptheArc1 = ptheArc1->hlink;
61deef 3098         bool NeedANS = 0;
6ff05a 3099         while (ptheArc1)
Q 3100         {
3101             //取得相连的虚节点地址
3102             node* pThisNode2 = ptheArc1->tailvex;
3103
3104             stProgSection prog1 = pThisNode2->prog1;
3105             if (prog1.Progs[0].nOpType1 == OP_AN) { prog1.Progs[0].nOpType1 = OP_ST; }
61deef 3106             else if (prog1.Progs[0].nOpType1 == OP_AN_) { prog1.Progs[0].nOpType1 = OP_ST_; }
Q 3107             else if (prog1.Progs[0].nOpType1 == OP_ST || prog1.Progs[0].nOpType1 == OP_ST_) {
3108                 prog1.Prefix += 1;
3109                 s1.Format(_T(" > 2 +1 %s"),prog1.ToText());    DbgLog(s1);
3110             }
3111             else {
3112                 prog1.Prefix += 0;
3113                 s1.Format(_T(" >2 +0 %s"),prog1.ToText());    DbgLog(s1);
3114             }
6ff05a 3115             if (prog1.Progs.size() > 1) {
Q 3116                 prog1.Append(CMTerm1Doc::stProg(OP_ORS));
61deef 3117                 NeedANS = 1;
6ff05a 3118             }
Q 3119             else {
3120                 if (pThisNode2->nType == typeNC) prog1.Progs[0].nOpType1 = OP_OR_;
3121                 else if (pThisNode2->nType == typeNO) prog1.Progs[0].nOpType1 = OP_OR;
3122                 else prog1.Progs[0].nOpType1 = OP_OR;
61deef 3123                 NeedANS = 1;
6ff05a 3124             }
Q 3125             prog2 += prog1;
3126
3127             arc* ptheArc2 = pThisNode2->firstIn;
3128             RemoveArc(ptheArc2->nId);                //删除弧
3129             arc* pTheNextArc = ptheArc1->hlink;        //取得下一个弧并保存
3130             RemoveArc(ptheArc1->nId);                //删除当前弧
3131             pThisNode2->bEnable = 0;                //删除实节点
3132             ptheArc1 = pTheNextArc;
3133         }
61deef 3134         if (theNode1.nType == -1 && theNode2.nType == -1 && NeedANS) { prog2.Append(CMTerm1Doc::stProg(OP_ANS)); }
6ff05a 3135         pThisNode1->prog1 = prog2;                //将所有程序汇总到第一个实节点
61deef 3136     //    pThisNode1->prog1.reduce();
6ff05a 3137     //    s1 = prog2.ToText(GetDocument());
Q 3138     //    DbgLog(_T("------ ") + s1);
3139     }
3140
3141     return 0;
3142 }
3143
3144 int CMTerm1View::RemoveArc(int nArcId)
3145 {
3146     arc& theArc = arcs[nArcId];
3147     node& theNode1 = *theArc.tailvex;
3148     node& theNode2 = *theArc.headvex;
3149     
3150     // 先看 Node1 这边, 
3151     // 首弧
3152     if (theNode1.firstOut == &theArc) {
3153         theNode1.firstOut = theArc.tlink;
3154     }
3155     else {
3156         arc* thatArc = theNode1.firstOut;
3157         while (thatArc->tlink !=0){
3158             if (thatArc->tlink == &theArc) {
3159                 thatArc->tlink = theArc.tlink;
3160                 break;
3161             }
3162             thatArc = thatArc->tlink;
3163         }
3164     }
3165     
3166
3167     // 再看 Node2 这边, 
3168     // 首弧
3169     if (theNode2.firstIn == &theArc) {
3170         theNode2.firstIn = theArc.hlink;
3171     }
3172     else {
3173         arc* thatArc = theNode2.firstIn;
3174         while (thatArc->hlink != 0) {
3175             if (thatArc->hlink == &theArc) {
3176                 thatArc->hlink = theArc.hlink;
3177                 break;
3178             }
3179             thatArc = thatArc->hlink;
3180         }
3181     }
3182
3183     theNode1.outdegree--;
3184     theNode2.indegree--;
3185     return nArcCount;
3186 }
3187
3188 int CMTerm1View::RemoveNode(int nNodeId)
3189 {
3190     node& theNode = nodes[nNodeId];
3191     theNode.bEnable = 0;
3192     if (theNode.indegree) {
3193
3194     }
3195     return nNodeCount;
3196 }
3197
3198 int CMTerm1View::MergeNode(int nNodeId1, int nNodeId2)        //合并两个串联的 实 Node
3199 {
3200     node& theNode1 = nodes[nNodeId1];
3201     node& theNode2 = nodes[nNodeId2];
3202     // 必须前者出度 为1 后者 入度 为1, 且 相连, 才能合并。
3203     // 先找到两者连接的弧
3204     if (!theNode1.bEnable || !theNode2.bEnable) return -1;
3205     if (theNode1.outdegree != 1 || theNode2.indegree != 1) return -2;
3206     if (theNode1.firstOut != theNode2.firstIn) return -3;
3207     // 删除两者之间的弧。
3208     RemoveArc(theNode1.firstOut->nId);
3209
3210     theNode1.firstOut = 0;
3211     theNode2.firstIn = 0;
3212
3213     // 将 Node2 的 出 弧, 转移 到 node1 上
3214     theNode1.CoilName += _T("  ") + theNode2.CoilName;
3215     theNode1.firstOut = theNode2.firstOut;
3216     theNode1.outdegree = theNode2.outdegree;
3217     theNode1.prog1 += theNode2.prog1;            // 段程序合并
3218
3219     arc* thatArc = theNode2.firstOut;
3220     while (thatArc != 0)
3221     {
3222         thatArc->tailvex = &theNode1;
3223         thatArc->tailNode = nNodeId1;
3224         thatArc = thatArc->tlink;
3225         theNode2.outdegree--;
3226     }
3227     // 
3228     // 现在 Node2 的入度和出度 均为 0, 删除 node2
3229     RemoveNode(nNodeId2);
3230     return 0;
3231 }
3232
3233 //  合并从 nNodeId 虚节点发出的 各个单行 Nodes; 直到下一个多输出的虚节点
3234 int CMTerm1View::MergeVPSubSerialNodes(int nNodeId)
3235 {
3236     node& theNode = nodes[nNodeId];
3237
3238     arc* theArc = theNode.firstOut;
3239     while (theArc != 0) {
3240         // 从当前弧 取出一个顶点
3241         node * thisNode = theArc->headvex;
3242         // 从这个顶点,找到下一个顶点
3243         if (thisNode->outdegree == 1 && thisNode->firstOut != 0) {
3244             node* thatNode = thisNode->firstOut->headvex;
3245             while (thatNode->indegree == 1 && thatNode->outdegree <= 1 && thatNode->nType != -2) {
3246                 if (thatNode->nType == typeOUT || thatNode->nType == typeSET || thatNode->nType == typeRESET) {
3247                     //break;
3248                 }
3249                 MergeNode(thisNode->nId, thatNode->nId);
3250                 if (thatNode->firstOut) thatNode = thatNode->firstOut->headvex;
3251                 else break;
3252             }
3253             if (thatNode->nType == -1) { //找到下一个虚顶点
3254                 if (!thatNode->OutProcAllDone) {
3255                     MergeVPSubSerialNodes(thatNode->nId);    //从虚顶点继续
3256                 }
3257             }
3258         }
3259         // 同一个出发点的 下一条弧
3260         theArc = theArc->tlink;
3261     };
3262     theNode.OutProcAllDone = 1;
3263
3264     return 0;
3265 }
3266
3267 //  合并从 nNodeId 虚节点发出的 各个单行 Nodes; 直到下一个 多输出的虚节点
3268 int CMTerm1View::MergeVPSerialNodes(int nNodeId)
3269 {
3270     node& theNode = nodes[nNodeId];
3271
3272     arc* theArc = theNode.firstOut;
3273     while (theArc != 0) {
3274         // 从当前弧 取出一个顶点
3275         node* thisNode = theArc->headvex;
3276         // 从这个顶点,找到下一个顶点
3277         if (thisNode->outdegree == 1 && thisNode->firstOut != 0) {
3278             node* thatNode = thisNode->firstOut->headvex;
3279             while (thatNode->nType != -2 && thatNode->indegree ==1 && thatNode->outdegree <= 1) {
3280                 if (thatNode->nType == typeOUT || thatNode->nType == typeSET || thatNode->nType == typeRESET) {
3281                     //break;
3282                 }
3283                 MergeNode(thisNode->nId, thatNode->nId);
3284                 if (thatNode->firstOut) thatNode = thatNode->firstOut->headvex;
3285                 else break;
3286             }
3287             if (thatNode->nType == -1) { //找到下一个虚顶点
3288                 if (!thatNode->OutProcAllDone) {
3289                     MergeVPSerialNodes(thatNode->nId);    //从虚顶点继续
3290                 }
3291             }
3292         }
3293         // 同一个出发点的 下一条弧
3294         theArc = theArc->tlink;
3295     };
3296     theNode.OutProcAllDone = 1;
3297
3298     return 0;
3299 }
3300
3301 //从 X,Y 点,向上查找 虚节点,最多终止于 endy;
3302 int CMTerm1View::FindVPNode(int x, int y, int endy)
3303 {
3304     int nNodeId = 0;
3305     for (int i = nNodeCount -1 ; i>=1; i--) {
3306         if (nodes[i].bEnable && nodes[i].nType == -1 && nodes[i].nCellX == x && nodes[i].nCellY <= y &&nodes[i].nCellY >=endy  )
3307         {
3308             nNodeId = i; break;
3309         }
3310     }
3311     return nNodeId;
3312 }
3313
3314
3315 int CMTerm1View::ScanVPAOV(int nVPNodeId1, int nVPNodeId2)
3316 {
3317     MergeParallelNodeWithinVP(nVPNodeId1, nVPNodeId2);
3318     return 0;
3319 }
3320 int CMTerm1View::ScanAOV1(int nNodeId)
3321 {
3322     node& theNode = nodes[nNodeId];
3323     CString s1;
3324     int nInput = theNode.indegree;
3325     int nOutput = theNode.outdegree;
3326     //    s1.Format(_T("%d type %d op %s coil %s  in %d   out %d"), theNode.nId, theNode.nType, theNode.Op, theNode.CoilName, theNode.indegree, theNode.outdegree);
3327     //    DbgLog(s1);
3328     if (theNode.InProcCount < theNode.indegree) return 0;
3329     // 虚拟结点,完成所有输入。
3330
3331     stProgSection prog2;
3332     if (theNode.outdegree > 0) {
3333         //  一直搜索下去,遇到 输入不为0的 虚节点 时 停止,进行下一个迭代
3334         arc* theArc = theNode.firstOut;
3335         int allOutputMerged = 1;
3336         int allOutputSimple = 1;
3337         for (int i = 0; i < nOutput && theArc != 0; i++) {
3338             node* thisNode = theArc->headvex;
3339             thisNode->InProcCount++;
3340             s1.Format(_T("- %d type %d op %s coil %s  in %d   out %d"), thisNode->nId, thisNode->nType, thisNode->Op, thisNode->CoilName, thisNode->indegree, thisNode->outdegree);
3341             DbgLog(s1);
3342             s1 = thisNode->prog1.ToText();
61deef 3343             DbgLog(_T("------ \r\n") + s1);
6ff05a 3344
Q 3345             arc* thisArc = thisNode->firstOut;
3346             if (thisNode->outdegree > 0) { allOutputMerged = 0; }
61deef 3347             if (thisNode->nType == typeOUT || thisNode->nType == typeSET || thisNode->nType == typeRESET) {
Q 3348                 thisNode->prog1.bModifyVal = 0;
3349             }
3350             else {
3351                 allOutputSimple = 0;
3352                 thisNode->prog1.bModifyVal = 1;
3353             }
6ff05a 3354             while (thisArc) {
Q 3355                 thisNode = thisArc->headvex;
3356                 thisNode->InProcCount++;
3357                 s1.Format(_T("-- %d type %d op %s coil %s  in %d   out %d"), thisNode->nId, thisNode->nType, thisNode->Op, thisNode->CoilName, thisNode->indegree, thisNode->outdegree);
3358                 DbgLog(s1);
3359                 if (thisNode->nType > 0) //thatNode.indegree == 1 && thatNode.outdegree == 1) 
3360                 {
3361                  thisArc = thisNode->firstOut;
3362                     //    node* thatNode = thisArc->headvex;
3363
3364                 }
3365                 else {
3366                     ScanVPAOV(nNodeId, thisNode->nId);
3367
3368                     if (thisNode->InProcCount >= thisNode->indegree) {
3369                         s1.Format(_T("-> %d type %d op %s coil %s  in %d   out %d"), thisNode->nId, thisNode->nType, thisNode->Op, thisNode->CoilName, thisNode->indegree, thisNode->outdegree);
3370                         DbgLog(s1);
3371
3372                         ScanAOV1(thisNode->nId);
3373                     }
3374                     break;
3375                 }
3376             }
3377             //            if (thatNode.nType > 0) {
3378             //                prog2.Append(thatNode.prog1);
3379             //            }
3380                         //RemoveArc(theArc->nId);
3381                         // 同一个出发点的 下一条弧
3382             theArc = theArc->tlink;
3383         }
3384         if (theNode.outdegree >= 2 && allOutputMerged) {
3385             s1.Format(_T(" Merge Output %d  %d  allsimple = %d "), nNodeId,theNode.outdegree,allOutputSimple);
3386             DbgLog(s1);
3387             if (allOutputSimple) {
3388                 arc * thisArc = theNode.firstOut;
3389                 node* thisNode = thisArc->headvex;
3390                 thisArc = thisArc->tlink;
3391                 for (int i = 1; i < nOutput && thisArc != 0; i++) {
3392                     node* thatNode = thisArc->headvex;
3393                     thisNode->prog1 += thatNode->prog1;
3394                     arc * tempArc = thisArc->tlink;
3395                     RemoveArc(thisArc->nId);
3396                     thisArc = tempArc;
3397                     RemoveNode(thatNode->nId);
3398                 }
3399             }
3400             else {
3401                 arc* thisArc = theNode.firstOut;
3402                 node* thisNode = thisArc->headvex;
3403                 stProgSection prog2;
3404                 prog2.Append(CMTerm1Doc::stProg(OP_PSHS));
61deef 3405                 int bLastModify = 1;
6ff05a 3406                 prog2 += thisNode->prog1;
61deef 3407                 if (thisNode->prog1.bModifyVal == 0) { bLastModify = 0; s1.Format(_T(" ModifyVal = 0, %s"), thisNode->prog1.ToText()); }
6ff05a 3408                 thisArc = thisArc->tlink;
61deef 3409
6ff05a 3410                 for (int i = 1; i < nOutput  && thisArc != 0; i++) {
Q 3411                     node* thatNode = thisArc->headvex;
3412                     if (i == nOutput - 1) { // 最后一个
3413                         prog2.Append(CMTerm1Doc::stProg(OP_POPS));
3414                     }
3415                     else {
61deef 3416                         if (bLastModify) { prog2.Append(CMTerm1Doc::stProg(OP_RDS)); }
6ff05a 3417                     }
61deef 3418                     if (thisNode->prog1.bModifyVal == 0) { bLastModify = 0;s1.Format(_T(" ModifyVal = 0, %s"), thisNode->prog1.ToText()); }
Q 3419                     else { bLastModify = 1; }
6ff05a 3420                     prog2 += thatNode->prog1;
Q 3421                     arc* tempArc = thisArc->tlink;
3422                     RemoveArc(thisArc->nId);
3423                     thisArc = tempArc;
3424                     RemoveNode(thatNode->nId);
3425                 }
3426                 thisNode->prog1 = prog2;
3427             }
3428         }
3429     }
3430
3431     return 0;
3432     /*
3433         node& theNode = nodes[nNodeId];
3434
3435         arc* theArc = theNode.firstOut;
3436         while (theArc != 0) {
3437             // 从当前弧 取出一个顶点
3438             node* thisNode = theArc->headvex;
3439             // 从这个顶点,找到下一个顶点
3440             if (thisNode->outdegree == 1 && thisNode->firstOut != 0) {
3441                 node* thatNode = thisNode->firstOut->headvex;
3442                 while (thatNode->nType != -1) {
3443                     if (thatNode->nType == typeOUT || thatNode->nType == typeSET || thatNode->nType == typeRESET) {
3444                         break;
3445                     }
3446                     MergeNode(thisNode->nId, thatNode->nId);
3447                     if (thatNode->firstOut) thatNode = thatNode->firstOut->headvex;
3448                     else break;
3449                 }
3450                 if (thatNode->nType == -1) { //找到下一个虚顶点
3451                     if (!thatNode->OutProcAllDone) {
3452                         MergeSerialNodes(thatNode->nId);    //从虚顶点继续
3453                     }
3454                 }
3455             }
3456             // 同一个出发点的 下一条弧
3457             theArc = theArc->tlink;
3458         };
3459         theNode.OutProcAllDone = 1;
3460     */
3461 }
3462
3463 /// <summary>
3464 /// 试用 AOV 方式 梯形图转Prog
3465 /// </summary>
3466 /// <returns></returns>
3467 int CMTerm1View::TransLDSToProgAOV()
3468 {
3469     CMTerm1Doc* pDoc = GetDocument();
3470     CString s1;
3471     s1.Format(_T("Trans LDS to PRrog"));
3472     DbgLog(s1);
3473     s1.Format(_T("AOV 方式 将梯形图转成prog格式"));
3474     DbgLog(s1);
3475
3476     //梯形图 ROW数量
3477     s1.Format(_T("总计行数 %d"), m_nTotalRow);
3478     DbgLog(s1);
3479     s1.Format(_T("Total Lines %d"), m_nTotalRow);
3480     DbgLog(s1);
3481
3482     //分段
3483     int nDivCount = 0;
3484     //分段 点集合
3485     int Divs[100] = { 0 };
3486     for (int i = 0; i < m_nTotalRow+5 ; i++)
3487     {
3488         int nRow = i;
3489         int bConnected = 0;
3490         //扫描程序,建立十字链表?
3491         for (int j = 0; j < m_CellPerLine; j++)
3492         {
3493             int nCol = j;
3494             if (Cells[nRow][nCol].bLeftLineDn)
3495             {
3496                 bConnected = 1;
3497                 //s1.Format(_T("row==%d col==%d 有左下竖线!!!"), nRow, nCol);
3498                 //DbgLog(s1);
3499                 break;
3500             }
3501         }
3502         if (!bConnected)
3503         {
3504             //找到一处分界点
3505             Divs[nDivCount] = i;
3506             s1.Format(_T("Div at Line %d 是 ::::::::::::分界点"), nRow);
3507             DbgLog(s1);
3508             nDivCount++;
3509         }
3510     }
3511     stProgSection allprogs;
3512     //每段单独处理
3513     for (int i = 0; i < nDivCount; i++)
3514     {
3515         int nStartLine, nEndLine;
3516         nNodeCount = 0;
3517         if (i == 0)
3518         {
3519             nStartLine = 0;
3520             nEndLine = Divs[i];
3521         }
3522         else
3523         {
3524             nStartLine = Divs[i - 1] + 1;
3525             nEndLine = Divs[i];
3526         }
3527         s1.Format(_T("本段行号 起始-终止: %d - %d "), nStartLine, nEndLine);
3528         DbgLog(s1);
3529         //s1.Format(_T("Process Line %d - %d "), nStartLine, nEndLine);
3530         //DbgLog(s1);
3531         int nCounts[20] = { 0 };
3532         int nCounts2[20] = { 0 };
3533         int nCounts3[20] = { 0 };
3534         s1.Empty();
3535         stProgSection section1;
3536         CString s2;
3537         int PrevNode = 0;
3538         nNodeCount = 1;        //清理存储的顶点和弧数据。
3539         nArcCount = 1;
3540         AddNode(-2, 0, 0, _T("Mother"));        //增加母线顶点
3541         for (int j = nStartLine; j <= nEndLine; j++) {
3542             int nPosX = 0;
3543             PrevNode = 1;        //从母线开始
3544             s1.Empty();
3545             for (int k = 0; k < m_CellPerLine; k++) {
3546                 stCell theCell = Cells[j][k];
3547                 int nNextX = 1;
3548                 int nType;
3549                 int bRightLineUp = 0;
3550                 if (k < m_CellPerLine - 1) { bRightLineUp = Cells[j][k + 1].bLeftLineUp; }
3551                 nType = theCell.nType;
3552                 if (nType == typeNone) { PrevNode = 0;  } // 不连接母线;
3553                 if (nType ) {
3554                     if (nType == typeLine1 && !theCell.bLeftLineUp && !theCell.bLeftLineDn && !bRightLineUp) continue;
3555                     if (nType == typeExt1 || nType == typeExt2 || nType == typeExt3 || nType == typeExt4) continue;
3556                     if (k!=0 && theCell.bLeftLineDn && !theCell.bLeftLineUp) {
3557                         PrevNode = AddNode(-1, k, j, _T("VP"),PrevNode);
3558                     }
3559                     if (k != 0 && theCell.bLeftLineUp) {
3560                         int VPNodeId = 0;
3561                             VPNodeId = FindVPNode(k , j,  nStartLine);
3562                         PrevNode = VPNodeId;
3563                     }
3564
3565
3566                     switch (nType) {
3567                     case typeLine1:
3568
3569                         break;
61deef 3570                     case typeEND:
Q 3571                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3572                         break;
6ff05a 3573                     case typeNO:
Q 3574                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3575                         break;
3576                     case typeNC:
3577                         PrevNode = AddNode(nType, k, j, theCell.sCoilName +_T("/"), PrevNode);
3578                         break;
3579                     case typePP:
3580                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3581                         break;
3582                     case typePN:
3583                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3584                         break;
3585                     case typeNOT:
3586                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3587                         break;
3588                     case typeDF:
3589                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3590                         break;
3591                     case typeDF_:
3592                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3593                         break;
3594                     case typeOUT:
3595                     case typeSET:
3596                     case typeRESET:
3597                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3598                         break;
3599                     case typeCMP:
3600                         nNextX = 3;
3601                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3602                         break;
3603                     case typeExt1:
3604                     case typeExt2:
3605                     case typeExt3:
3606                         break;
3607                     case typeTM:
3608                         nNextX = 3;
3609                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3610                         break;
3611                     case typeFN1:
3612                         nNextX = 2;
3613                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3614                         break;
3615                     case typeFN2:
3616                         nNextX = 3;
3617                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3618                         break;
3619                     case typeFN3:
3620                         nNextX = 4;
3621                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3622                         break;
3623                     case typeFN4:
3624                         nNextX = 5;
3625                         PrevNode = AddNode(nType, k, j, theCell.sCoilName, PrevNode);
3626                         break;
3627                     case typeCoil:
3628                         break;
3629                     default:
3630                         break;
3631                     }
3632                     s2 = Cells[j][k].sCoilName;
3633                     //k += nStep - 1;
3634                     s1 += s2 + _T(" ") + intToString(nNextX) + _T("  ");
3635
3636                     if (bRightLineUp) {
3637                         int VPNodeId = 0;
3638                             VPNodeId = FindVPNode(k + 1, j, nStartLine);
3639                         AddArc(PrevNode, VPNodeId);
3640                         PrevNode = VPNodeId;
3641                     }
3642                 }
3643             }
3644             DbgLog(s1);
3645         }
3646         //输出已经生成的 AOV 图 顶点信息
3647         for (int j = 1; j < nNodeCount; j++) {
61deef 3648             s1.Format(_T("%d    %d %s %s  in %d  out %d  %s "), j, nodes[j].nType,nodes[j].Op, nodes[j].CoilName,nodes[j].indegree,nodes[j].outdegree, nodes[j].prog1.ToText());
Q 3649             DbgLog(s1);
6ff05a 3650         }
Q 3651         //输出AOV图的 弧 数据 
3652         for (int j = 1; j < nArcCount; j++) {
3653             s1.Format(_T("%3d     %2d - %2d "), j, arcs[j].tailNode, arcs[j].headNode);
3654 //            DbgLog(s1);
3655         }
3656
3657         for (int n = 1; n < 8; n++) {
3658             s1.Format(_T("处理步骤 %d "), n);
3659             DbgLog(s1);
3660             for (int j = 1; j < nNodeCount; j++) {
3661                 if (nodes[j].bEnable) nodes[j].OutProcAllDone = 0;
3662             }
3663             // 处理 AOV 图
3664             // 从 母线 开始 
3665             //串联归并 // 归并原则, 普通节点,非虚节点, 两个虚节点之间 多个连续的,归并, 非输出。
61deef 3666             s1.Format(_T("合并串联的节点 %d "), n);
Q 3667             DbgLog(s1);
6ff05a 3668             MergeVPSubSerialNodes(1);
Q 3669             // 处理虚节点
3670             // 虚节点的多输入处理, 单 OR 或者 多 ORS。
3671             // 虚节点的输出处理, 
3672             // 对于后续还有共同虚节点的输出, 第一个不处理,
3673             // 第二个,单不处理,多处理 ST, 后面由虚节点再 ORS, ANS。
3674             // 对于直接输出的,如果后面没有改变的输出, 直接输出不处理。
3675             // 对于后面还有改变的, PSHS, RDS, POPS
3676             // 另外,可以后期简化, ST 后紧跟 ORS 的, 简化为 OR。
3677             // PSHS RDS POPS 后跟不改变的。 简化
61deef 3678             s1.Format(_T("处理虚节点的输出 %d "), n);
Q 3679             DbgLog(s1);
6ff05a 3680             ScanAOV1(1);
Q 3681             if (nodes[2].outdegree == 0) break;
3682         }
3683         // 输出处理完的 AOV 图
3684         s1.Format(_T("处理完的AOV图"));
3685         DbgLog(s1);
3686         for (int j = 2; j < nNodeCount; j++) {
3687             CStringA s2;
3688             if (nodes[j].bEnable) {
3689                 s1.Format(_T("%d type %d op %s coil %s  in %d   out %d"), j, nodes[j].nType, nodes[j].Op, nodes[j].CoilName, nodes[j].indegree, nodes[j].outdegree);
3690                 DbgLog(s1);
3691                 s1 = nodes[j].prog1.ToText();
3692                 DbgLog(s1);
3693             }
3694         }
3695         allprogs += nodes[2].prog1;
3696         nodes[2].prog1.Progs.clear();
3697     }
3698     s1.Format(_T("完整的PLC程序 \r\n"));
3699     s1 += allprogs.ToText();
3700     DbgLog(s1);
3701     // 创建 AOV 图
3702
3703     //输出程序
3704     int n = (int)allprogs.Progs.size();
3705     s1.Format(_T("总程序步数 %d "), n);
3706     DbgLog(s1);
3707     s1.Format(_T("all prog steps %d "), n);
3708     DbgLog(s1);
3709     for (int i = 0; i < n; i++)
3710     {
3711         int optype = allprogs.Progs[i].nOpType1;
3712         allprogs.Progs[i].PairTo = 0;//??????????
3713         allprogs.Progs[i].nBinStep = i;
3714         CStringA OpTxtA, OpShowTxtA;
3715         CString OpTxt, OpShowTxt;
3716         pDoc->OpToTxt(optype, OpTxtA);
3717         pDoc->OpToShowTxt(optype, OpShowTxtA);
3718         OpTxt = OpTxtA;
3719         OpShowTxt = OpShowTxtA;
3720         s1.Format(_T("%d %s %s"), optype, OpTxt, OpShowTxt);
3721         pDoc->Progs[i] = allprogs.Progs[i];
3722         DbgLog(s1);
3723     }
3724     pDoc->m_nProgSteps = n;
418cb3 3725     return 0;
Q 3726 }
4dfb88 3727
d34256 3728 /// <summary>
Z 3729 /// 梯形图转Prog
3730 /// </summary>
3731 /// <returns></returns>
418cb3 3732 int CMTerm1View::TransLDSToProg()
Q 3733 {
3734     CMTerm1Doc * pDoc = GetDocument();
3735     CString s1;
3736     s1.Format(_T("Trans LDS to PRrog"));
3737     DbgLog(s1);
e55aec 3738     s1.Format(_T("将梯形图转成prog格式"));
Z 3739     DbgLog(s1);
418cb3 3740
ad1b4b 3741     //梯形图 ROW数量
e55aec 3742     s1.Format(_T("总计行数 %d"), m_nTotalRow);
Z 3743     DbgLog(s1);
418cb3 3744     s1.Format(_T("Total Lines %d"), m_nTotalRow);
Q 3745     DbgLog(s1);
e55aec 3746     
418cb3 3747     //分段
Q 3748     int nDivCount = 0;
e55aec 3749     //分段 点集合
418cb3 3750     int Divs[100] = { 0 };
ad1b4b 3751     for (int i = 0; i < m_nTotalRow; i++)    
Z 3752     {
418cb3 3753         int nRow = i;
Q 3754         int bConnected = 0;
aac3b3 3755          for (int j = 0; j < m_CellPerLine; j++)        
ad1b4b 3756         {
418cb3 3757             int nCol = j;
ad1b4b 3758             if (Cells[nRow][nCol].bLeftLineDn) 
Z 3759             {
e55aec 3760                 bConnected = 1; 
Z 3761                 s1.Format(_T("row==%d col==%d 有左下竖线!!!"), nRow,nCol);
3762                 DbgLog(s1);
3763                 break;
418cb3 3764             }
ad1b4b 3765           }
Z 3766         if (!bConnected) 
3767         {
418cb3 3768             //找到一处分界点
Q 3769             Divs[nDivCount] = i;
ad1b4b 3770             s1.Format(_T("Div at Line %d 是 ::::::::::::分界点"), nRow);
418cb3 3771             DbgLog(s1);
Q 3772             nDivCount++;
3773         }
3774     }
ad1b4b 3775
aac3b3 3776      stProgSection allprogs;
418cb3 3777     //每段单独处理
ad1b4b 3778     for (int i = 0; i < nDivCount; i++)    
Z 3779     {
418cb3 3780         int nStartLine, nEndLine;
ad1b4b 3781         if (i == 0) 
Z 3782         {
e55aec 3783             nStartLine = 0; 
Z 3784             nEndLine = Divs[i]; 
4ed7fc 3785          }
ad1b4b 3786         else 
Z 3787         {
e55aec 3788             nStartLine = Divs[i - 1]+1;
Z 3789             nEndLine = Divs[i]; 
ad1b4b 3790         }
e55aec 3791         s1.Format(_T("本段行号 起始-终止: %d - %d "), nStartLine, nEndLine);
Z 3792         DbgLog(s1);
418cb3 3793         s1.Format(_T("Process Line %d - %d "), nStartLine, nEndLine);
Q 3794         DbgLog(s1);
3795         int nCounts[20] = { 0 };
3796         int nCounts2[20] = { 0 };
3797         int nCounts3[20] = { 0 };
3798
3799         s1.Empty();
ad1b4b 3800         for (int j = 0; j < m_CellPerLine; j++)    
Z 3801         {
418cb3 3802             int nCount = 0;
Q 3803             int nCount2 = 0;
3804             int nCount3 = 0;
ad1b4b 3805             for (int k = nStartLine; k <= nEndLine; k++) 
Z 3806             {
3807                 if (Cells[k][j].nType) 
3808                 {
418cb3 3809                     nCount += 1;
Q 3810                     nCount2 += 1;
3811                     nCount3 += 1;
e55aec 3812                     if (Cells[k][j].bLeftLineUp)
Z 3813                     {
3814                         nCount2 -= 1;
3815                     }
418cb3 3816 //                    if (Cells[k][j].bLeftLineDn) nCount2 -= 1;
ad1b4b 3817
Z 3818                     if (j != m_CellPerLine - 1)    
3819                     {
e55aec 3820                         if (Cells[k][j + 1].bLeftLineUp)
Z 3821                         {
3822                             nCount3 -= 1;
3823                         }
418cb3 3824 //                        if (Cells[k][j + 1].bLeftLineDn) nCount3 -= 1;
Q 3825                     }
3826                 }
3827             }
3828             nCounts[j] = nCount;
3829             nCounts2[j] = nCount2;
3830             nCounts3[j] = nCount3;
3831         }
ad1b4b 3832
418cb3 3833         s1.Empty();
ad1b4b 3834         for (int j = 0; j < m_CellPerLine; j++) 
Z 3835         {
418cb3 3836             s1.AppendFormat(_T(" %d(%d)"), nCounts[j],nCounts3[j]);
Q 3837         }
e55aec 3838         DbgLog(_T(""));
ad1b4b 3839
418cb3 3840         DbgLog(s1);
Q 3841         s1.Empty();
ad1b4b 3842         for (int j = 0; j < m_CellPerLine; j++)    
Z 3843         {
418cb3 3844             s1.AppendFormat(_T(" %d "), nCounts2[j]);
Q 3845         }
3846         DbgLog(s1);
3847         //开始从左到右,从上到下扫描,主要关注 竖直连接线。
3848         int nCurPosX,nCurPosY;
3849         nCurPosY = nStartLine;
3850         nCurPosX = 0;
3851         CString sProg;
3852         int nAllSteps=0;
3853         stProgSection Progsec;
e55aec 3854         for (int i = nStartLine; i <= nEndLine; i++)
Z 3855         {
418cb3 3856             CString sProgSec;
Q 3857             int nSteps = 0;;
3858             nCurPosY = i;
3859             stProgSection thisprogsec;
3860             if (Cells[i][0].nType)
d34256 3861             {
e55aec 3862                 firstCoil = true;
ad1b4b 3863                 //循环遍历单元格(转换的逻辑在这个函数)
4ed7fc 3864                 //ScanLDSCells(nStartLine, nEndLine, nCurPosY, nCurPosX, 0, thisprogsec, sProgSec, nSteps);
Z 3865                 //ScanLDSCells2(nStartLine, nEndLine, nCurPosY, nCurPosX, 0, thisprogsec, sProgSec, nSteps);
d34256 3866             }
4ed7fc 3867             //sProg += sProgSec;
Z 3868          //    nAllSteps += nSteps;
3869             //Progsec += thisprogsec;
418cb3 3870         }
4ed7fc 3871         CString sProgSec;
Z 3872         int nSteps = 0;;
3873         nCurPosY = i;
3874         stProgSection thisprogsec;
3875         ScanLDSCells2(nStartLine, nEndLine, nCurPosY, nCurPosX, 16,0, thisprogsec, sProgSec, nSteps);
3876         sProg += sProgSec;
3877         nAllSteps += nSteps;
3878         Progsec += thisprogsec;
418cb3 3879         DbgLog(_T("\r\n")+ sProg);
Q 3880         int n = int(Progsec.Progs.size());
e55aec 3881         s1.Format(_T("程序段步数: %d "), n);
Z 3882         DbgLog(s1);
418cb3 3883         s1.Format(_T("progSec steps %d "), n);
Q 3884         DbgLog(s1);
ad1b4b 3885         for (int i = 0; i < n; i++) 
Z 3886         {
418cb3 3887             int optype = Progsec.Progs[i].nOpType1;
Q 3888             CStringA OpTxtA, OpShowTxtA;
3889             CString OpTxt, OpShowTxt;
3890             pDoc->OpToTxt(optype, OpTxtA);
3891             pDoc->OpToShowTxt(optype, OpShowTxtA);
3892             OpTxt = OpTxtA;
3893             OpShowTxt = OpShowTxtA;
3894             s1.Format(_T("%d %s %s"), optype, OpTxt, OpShowTxt);
3895             DbgLog(s1);
3896         }
3897         allprogs += Progsec;
3898     }
ad1b4b 3899
418cb3 3900     //输出程序
Q 3901     int n=(int)allprogs.Progs.size();
e55aec 3902     s1.Format(_T("总程序步数 %d "), n);
Z 3903     DbgLog(s1);
418cb3 3904     s1.Format(_T("all prog steps %d "), n);
Q 3905     DbgLog(s1);
ad1b4b 3906     for (int i = 0; i < n; i++)    
Z 3907     {
418cb3 3908         int optype=allprogs.Progs[i].nOpType1;
4ed7fc 3909         allprogs.Progs[i].PairTo = 0;//??????????
df0321 3910         allprogs.Progs[i].nBinStep = i;
418cb3 3911         CStringA OpTxtA,OpShowTxtA;
Q 3912         CString OpTxt,OpShowTxt;
3913         pDoc->OpToTxt(optype, OpTxtA);
3914         pDoc->OpToShowTxt(optype, OpShowTxtA);
3915         OpTxt = OpTxtA;
3916         OpShowTxt = OpShowTxtA;
3917         s1.Format(_T("%d %s %s"), optype, OpTxt, OpShowTxt);
df0321 3918         pDoc->Progs[i] = allprogs.Progs[i];
4dfb88 3919         DbgLog(s1);
418cb3 3920     }
df0321 3921     pDoc->m_nProgSteps = n;
418cb3 3922     return 0;
Q 3923 }
3924
d34256 3925
Z 3926 /// <summary>
3927 /// :绘制每个单元格的内容
3928 /// </summary>
3929 /// <param name="nStartLine"></param>
3930 /// <param name="nEndLine"></param>
aac3b3 3931 /// <param name="nPosY">行</param>
Z 3932 /// <param name="nPosX">列</param>
3933 /// <param name="nLevel">层级</param>
e55aec 3934 /// <param name="progsec">prog格式的指令集</param>
Z 3935 /// <param name="sProgSec">指令集</param>
3936 /// <param name="nSteps">程序步数</param>
d34256 3937 /// <returns></returns>
aac3b3 3938 int CMTerm1View::ScanLDSCells(int nStartLine, int nEndLine, int nPosY, int nPosX,
Z 3939     int nLevel, stProgSection & progsec, CString & sProgSec, int &nSteps)
418cb3 3940 {
Q 3941     CString s1;
3942     int nCurPosX, nCurPosY;
4ed7fc 3943     int nNextX = 1;//步长(下个起始点移动的距离)
418cb3 3944     nCurPosY = nPosY;
Q 3945     nCurPosX = nPosX;
6ff05a 3946 //    int nCoilType, CoilAddr;
df0321 3947     CMTerm1Doc* pDoc = GetDocument();
ad1b4b 3948     for (int j = nPosX; j < m_CellPerLine; j += nNextX)
Z 3949     {
418cb3 3950         nCurPosX = j;
4ed7fc 3951         //先处理当前单元基本信息;
418cb3 3952         int nType = Cells[nCurPosY][nCurPosX].nType;
Q 3953         CString sCellName = Cells[nCurPosY][nCurPosX].sCoilName;
3954         CMTerm1Doc::stProg theprog;
df0321 3955         CStringA sCellNameA;
Q 3956         sCellNameA = sCellName;
ad1b4b 3957
e55aec 3958         if (j + nNextX >= m_CellPerLine)
Z 3959         {
3960             continue;
3961         }
3962
3963         //1.先获取此单元格右侧一格的竖线
3964         if (Cells[nCurPosY][j + nNextX].bLeftLineUp
3965             || Cells[nCurPosY][j + nNextX].bLeftLineDn)
3966         {
3967
4ed7fc 3968             //先看往上面有没有连接
Z 3969             if (Cells[nCurPosY][j + nNextX].bLeftLineUp)
3970             {
3971                 // 往上面有连接且有触点连接,才使用ORS
3972                 s1.Format(_T("%d %d ORS "), nCurPosY, nCurPosX);
3973                 DbgLog(s1);
3974                 theprog.nOpType1 = OP_ORS;
3975                 progsec.Append(theprog);
3976                 sProgSec.AppendFormat(_T("ORS \r\n"));
3977                 firstCoil = false;
3978                 nSteps += 1;
3979                 nLevel -= 1;
3980             }
3981             //右侧一格的左上是否有链接
e55aec 3982             int nLeftUpCon = 0;
Z 3983             if (Cells[nCurPosY][j + nNextX].bLeftLineUp)
3984             {
3985                 nLeftUpCon = 1;
3986             }
4ed7fc 3987             //向下查找,看看竖线的右侧一格的左侧下面还有没有连接其他东西
Z 3988             int nLeftDnCon = 0;//单元格右侧一格的左侧向下连接数
3989             for (int k = nCurPosY; k <= nEndLine; k++)
e55aec 3990             {
Z 3991                 if (Cells[k][j + nNextX].bLeftLineDn)
3992                 {
3993                     if (Cells[k][j + nNextX - 1].nType)
3994                     {
3995                         nLeftDnCon += 1;
3996                     }
3997                 }
3998                 else
3999                 {
4000                     break;  // 竖线到最下面的端点了。
4001                 }
4002             }
4003
4004             s1.Format(_T("LeftUp %d   LeftDn  %d"), nLeftUpCon, nLeftDnCon);
4005             DbgLog(s1);
4006
4ed7fc 4007             //右侧一格的左侧下面有连接,那么扫描到这个竖线时返回,继续扫描左侧下面的内容。
e55aec 4008             if (nLeftDnCon)
Z 4009             {
4010                 return 1;
4011             }
4ed7fc 4012             //右侧一格的左侧下面没有连接,那么这个就是左面最后的单元,开始处理右面的单元。
e55aec 4013             else
Z 4014             {
4015                 if (nLeftUpCon)
4016                 {
4017                     if (nPosX > 0 || nLevel > 0)
4018                     {
4019                         s1.Format(_T("%d %d ANS "), nCurPosY, nCurPosX);
4020                         DbgLog(s1);
4021                         theprog.nOpType1 = OP_ANS;
4022                         progsec.Append(theprog);
4023                         sProgSec.AppendFormat(_T("ANS \r\n"));
4024                         nSteps += 1;
4025                         nLevel -= 1;
4026                     }
4027                 }
4028                 //从头到尾处理, 查找此竖线的最高位置;
4029                 int nLineTop = nCurPosY;
4030                 int nLineBottom = nCurPosY;
4031                 for (int k = nCurPosY; k >= nStartLine; k--)
4032                 {
4033                     if (!Cells[k][j + nNextX].bLeftLineUp)
4034                     {
4035                         break;
4036                     }
4037                     nLineTop = k - 1;
4038                 }
4039
4040                 // 查找右侧有几个连接
4041                 int nRightCon = 0;//单元格右侧连接数
4042                 for (int k = nLineTop; k <= nEndLine; k++)
4043                 {
4044                     if (Cells[k][j + nNextX].nType)
4045                     {
4046                         nRightCon += 1;
4047                     }
4048                     nLineBottom = k;
4049                     if (!Cells[k][j + nNextX].bLeftLineDn)
4050                     {
4051                         break;
4052                     }
4053                 }
4054                 s1.Format(_T("VLine %d - %d : %d , right = %d "), nLineTop, nLineBottom, j + nNextX, nRightCon);
4055                 DbgLog(s1);
4056
4057                 if (nRightCon == 1)
4058                 {
4ed7fc 4059                      s1.Format(_T(">>>> Go %d : %d , level %d "), nLineTop, j + nNextX, nLevel);
aac3b3 4060                     DbgLog(s1);
Z 4061                     CString ProgSec;
4062                     int theSteps = 0;
4063                     stProgSection thisprogsec;
e55aec 4064
4ed7fc 4065                     //这有问题,应该是在最高点的时候,单独进行一次转换?
aac3b3 4066                     int r = ScanLDSCells(nStartLine, nEndLine, nLineTop, j + nNextX, nLevel, thisprogsec, ProgSec, theSteps);
e55aec 4067
aac3b3 4068                     sProgSec += ProgSec;
Z 4069                     nSteps += theSteps;
4070                     progsec += thisprogsec;
4071                     s1.Format(_T("<<<< Re %d : %d , Result %d "), nLineTop, j + nNextX, 0);
4072                     DbgLog(s1);
4ed7fc 4073                     continue;
e55aec 4074                 }
Z 4075                 else
4076                 {
4077                     int nLastResult = 0;
4078                     int nRightCount = 0;
4079                     CString sCons[100];
4080                     CString ProgSecs[100];
4081                     int res[100] = { 0 };
4082                     int nLastSteps = 0;
4083                     for (int k = nLineTop; k <= nLineBottom; k++)
4084                     {
4085                         //s1.Format(_T("VLine %d - %d : %d       %d of %d "), nLineTop, nLineBottom, j + nNextX, k+1,nRightCon);
4086                         //DbgLog(s1);
4087                         if (Cells[k][j + nNextX].nType)
4088                         {
4089                             s1.Format(_T(" >>> Go %d : %d , level %d "), k, j + nNextX, nLevel + 1);
4090                             DbgLog(s1);
4091                             CString ProgSec;
4092                             int theSteps = 0;
4093                             nLevel += 1;
4094                             stProgSection thisprogsec;
4095                             res[nRightCount] = ScanLDSCells(nStartLine, nEndLine, k, j + nNextX, nLevel, thisprogsec, ProgSecs[nRightCount], theSteps);
4096                             nLastResult = res[nRightCount];
4097                             nSteps += theSteps;
4098                             progsec += thisprogsec;
4099                             //if (res[nRightCount] > 0) nLevel += 1;
4100                             sProgSec += ProgSec;
4101                             s1.Format(_T(" <<< Re %d : %d , Result %d Steps %d Last %d"), k, j + nNextX, res[nRightCount], theSteps, nLastSteps);
4102                             DbgLog(s1);
4103                             if (nRightCount == 0)
4104                             {
4ed7fc 4105                                 //这里是不是应该做点什么
e55aec 4106                             }
Z 4107                             else if (res[nRightCount - 1] == 0)
4108                             {
4109                                 s1.Format(_T(" POPS"), k, j + nNextX, nLevel + 1);
4110                                 DbgLog(s1);
4111                                 //sProgSec.AppendFormat(_T("POPS \r\n"));
4112                                 if (nLastSteps > 1)
4113                                 {
4114                                     if (sCons[nRightCount - 1] == _T("POPS"))
4115                                     {
4116                                         sCons[nRightCount - 1] = _T("RDS");
4117                                     }
4118                                     else
4119                                     {
4120                                         sCons[nRightCount - 1] = _T("PSHS");
4121                                     }
4122                                     sCons[nRightCount] = _T("POPS");
4123                                 }
4124                             }
4125                             else
4126                             {
4127
4128                             }
4129                             nLastSteps = theSteps;
4130                             nRightCount++;
4131                         }
4132                     }
4133                     nLastResult = 0;
4134                     for (int k = 0; k < nRightCount; k++)
4135                     {
4136                         if (nLastResult || res[k])
4137                         {
4138                             s1 = _T("ST") + ProgSecs[k];
4139
4140                             ProgSecs[k] = s1;
4141                         }
4142                         s1 = sCons[k] + _T("\r\n") + ProgSecs[k];
4143                         sProgSec.Append(s1);
4144                         nLastResult = res[k];
4145                     }
4146                     if (nLastResult)
4147                     {
4148                         sProgSec.Append(_T("ANS\r\n"));
4149                     }
4150                     return 0;
4151                 }
4152             }
4153         }
4ed7fc 4154         //如果没有竖线直接翻译
Z 4155         else
4156         {
4157             Translate2Prog(nType, j + nNextX, nLevel, sCellName, progsec, sProgSec, nSteps);
4158         }
4159         /*
e55aec 4160         #pragma region  根据单元格类型转换为指令和prog
Z 4161
4162         if (nType == typeNO)
d34256 4163         {
ad1b4b 4164             if (firstCoil && nType != typeLine1 && nType != typeLine2)
Z 4165             {
aac3b3 4166                 //先看往上面有没有连接
Z 4167                 if (Cells[nCurPosY][j + nNextX].bLeftLineUp)
4168                 {
4169                     // 往上面有连接且有触点连接,才使用OR
4170                     s1.Format(_T("%d %d OR %s"), nCurPosY, nCurPosX, sCellName);
4171                     sProgSec.AppendFormat(_T("OR %s\r\n"), sCellName);
4172                     theprog.nOpType1 = OP_OR;
4173                 }
4174                 else
4175                 {
4176                     s1.Format(_T("%d %d ST %s"), nCurPosY, nCurPosX, sCellName);
4177                     sProgSec.AppendFormat(_T("ST %s\r\n"), sCellName);
4178                     theprog.nOpType1 = OP_ST;
4179                 }
df0321 4180                 theprog.nParamCount = 1;
Q 4181                 pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4182                 theprog.Params[0].nParamType = nCoilType;
4183                 theprog.Params[0].nParamAddr = CoilAddr;
4184                 theprog.Params[0].sParamStr = sCellNameA;
418cb3 4185                 progsec.Append(theprog);
ad1b4b 4186                 firstCoil = false;
418cb3 4187             }
e55aec 4188             else
Z 4189             {
418cb3 4190                 s1.Format(_T("%d %d AN %s"), nCurPosY, nCurPosX, sCellName);
Q 4191                 sProgSec.AppendFormat(_T("NO %s\r\n"), sCellName);
4192                 theprog.nOpType1 = OP_AN;
df0321 4193                 theprog.nParamCount = 1;
Q 4194                 pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4195                 theprog.Params[0].nParamType = nCoilType;
4196                 theprog.Params[0].nParamAddr = CoilAddr;
4197                 theprog.Params[0].sParamStr = sCellNameA;
418cb3 4198                 progsec.Append(theprog);
Q 4199             }
4200             nSteps += 1;
4201             DbgLog(s1);
e55aec 4202             nNextX = 1;
ad1b4b 4203         }
e55aec 4204         else if (nType == typeNC)
ad1b4b 4205         {
Z 4206             if (firstCoil && nType != typeLine1 && nType != typeLine2)
4207             {
418cb3 4208                 s1.Format(_T("%d %d ST/ %s"), nCurPosY, nCurPosX, sCellName);
Q 4209                 sProgSec.AppendFormat(_T("ST/ %s\r\n"), sCellName);
4210                 theprog.nOpType1 = OP_ST_;
df0321 4211                 theprog.nParamCount = 1;
Q 4212                 pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4213                 theprog.Params[0].nParamType = nCoilType;
4214                 theprog.Params[0].nParamAddr = CoilAddr;
4215                 theprog.Params[0].sParamStr = sCellNameA;
418cb3 4216                 progsec.Append(theprog);
ad1b4b 4217                 firstCoil = false;
418cb3 4218             }
Q 4219             else
4220             {
4221                 s1.Format(_T("%d %d AN/ %s"), nCurPosY, nCurPosX, sCellName);
4222                 sProgSec.AppendFormat(_T("AN/ %s\r\n"), sCellName);
4223                 theprog.nOpType1 = OP_AN_;
df0321 4224                 theprog.nParamCount = 1;
Q 4225                 pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4226                 theprog.Params[0].nParamType = nCoilType;
4227                 theprog.Params[0].nParamAddr = CoilAddr;
4228                 theprog.Params[0].sParamStr = sCellNameA;
418cb3 4229                 progsec.Append(theprog);
Q 4230             }
4231             DbgLog(s1);
4232             nSteps += 1;
e55aec 4233             nNextX = 1;
ad1b4b 4234         }
e55aec 4235         else if (nType == typePP)
ad1b4b 4236         {
418cb3 4237             s1.Format(_T("%d %d PP %s"), nCurPosY, nCurPosX, sCellName);
Q 4238             DbgLog(s1);
4239             //progsec.Append(theprog);
4240             sProgSec.AppendFormat(_T("PP %s\r\n"), sCellName);
4241             nSteps += 1;
e55aec 4242             nNextX = 1;
ad1b4b 4243         }
e55aec 4244         else if (nType == typePN)
ad1b4b 4245         {
418cb3 4246             s1.Format(_T("%d %d PN %s"), nCurPosY, nCurPosX, sCellName);
Q 4247             DbgLog(s1);
4248             //progsec.Append(theprog);
4249             sProgSec.AppendFormat(_T("PN %s\r\n"), sCellName, sCellName);
4250             nSteps += 1;
e55aec 4251             nNextX = 1;
ad1b4b 4252         }
e55aec 4253         else if (nType == typeNOT)
ad1b4b 4254         {
418cb3 4255             s1.Format(_T("%d %d NOT %s"), nCurPosY, nCurPosX, sCellName);
Q 4256             DbgLog(s1);
4257             sProgSec.AppendFormat(_T("NOT %s\r\n"), sCellName);
4258             theprog.nOpType1 = OP_NOT;
4259             progsec.Append(theprog);
4260             nSteps += 1;
e55aec 4261             nNextX = 1;
ad1b4b 4262         }
Z 4263         else if (nType == typeDF)
4264         {
418cb3 4265             s1.Format(_T("%d %d DF %s"), nCurPosY, nCurPosX, sCellName);
Q 4266             DbgLog(s1);
4267             sProgSec.AppendFormat(_T("DF %s\r\n"), sCellName);
4268             theprog.nOpType1 = OP_DF;
4269             progsec.Append(theprog);
4270             nSteps += 1;
e55aec 4271             nNextX = 1;
ad1b4b 4272         }
Z 4273         else if (nType == typeDF_)
4274         {
418cb3 4275             s1.Format(_T("%d %d DF/ %s"), nCurPosY, nCurPosX, sCellName);
Q 4276             DbgLog(s1);
4277             sProgSec.AppendFormat(_T("DF/ %s\r\n"), sCellName);
4278             theprog.nOpType1 = OP_DF_;
4279             progsec.Append(theprog);
4280             nSteps += 1;
e55aec 4281             nNextX = 1;
ad1b4b 4282         }
Z 4283         else if (nType == typeOUT)
4284         {
418cb3 4285             s1.Format(_T("%d %d OUT %s"), nCurPosY, nCurPosX, sCellName);
Q 4286             DbgLog(s1);
4287             sProgSec.AppendFormat(_T("OUT %s\r\n"), sCellName);
4288             theprog.nOpType1 = OP_OUT;
df0321 4289             theprog.nParamCount = 1;
Q 4290             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4291             theprog.Params[0].nParamType = nCoilType;
4292             theprog.Params[0].nParamAddr = CoilAddr;
4293             theprog.Params[0].sParamStr = sCellNameA;
418cb3 4294             progsec.Append(theprog);
Q 4295             nSteps += 1;
e55aec 4296             nNextX = 1;
ad1b4b 4297         }
Z 4298         else if (nType == typeSET)
4299         {
418cb3 4300             s1.Format(_T("%d %d SET %s"), nCurPosY, nCurPosX, sCellName);
Q 4301             DbgLog(s1);
4302             sProgSec.AppendFormat(_T("SET %s\r\n"), sCellName);
4303             theprog.nOpType1 = OP_SET;
df0321 4304             theprog.nParamCount = 1;
Q 4305             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4306             theprog.Params[0].nParamType = nCoilType;
4307             theprog.Params[0].nParamAddr = CoilAddr;
4308             theprog.Params[0].sParamStr = sCellNameA;
418cb3 4309             progsec.Append(theprog);
Q 4310             nSteps += 1;
e55aec 4311             nNextX = 1;
ad1b4b 4312         }
Z 4313         else if (nType == typeRESET)
4314         {
418cb3 4315             s1.Format(_T("%d %d RESET %s"), nCurPosY, nCurPosX, sCellName);
Q 4316             DbgLog(s1);
4317             sProgSec.AppendFormat(_T("RESET %s\r\n"), sCellName);
4318             theprog.nOpType1 = OP_RESET;
df0321 4319             theprog.nParamCount = 1;
Q 4320             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4321             theprog.Params[0].nParamType = nCoilType;
4322             theprog.Params[0].nParamAddr = CoilAddr;
4323             theprog.Params[0].sParamStr = sCellNameA;
418cb3 4324             progsec.Append(theprog);
Q 4325             nSteps += 1;
e55aec 4326             nNextX = 1;
ad1b4b 4327         }
e55aec 4328         else if (nType == typeCMP)
ad1b4b 4329         {
e55aec 4330             s1.Format(_T("%d %d CMP %s %s %s"), nCurPosY, nCurPosX, sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
418cb3 4331             DbgLog(s1);
Q 4332             theprog.nOpType1 = OP_ST_GT;
df0321 4333             theprog.nParamCount = 1;
418cb3 4334             progsec.Append(theprog);
Q 4335             sProgSec.AppendFormat(_T("CMP %s %s %s \r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
4336             nSteps += 1;
e55aec 4337             nNextX = 3;
ad1b4b 4338         }
e55aec 4339         else if (nType == typeTM)
ad1b4b 4340         {
e55aec 4341             s1.Format(_T("%d %d TM %s %d %s"), nCurPosY, nCurPosX, sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
418cb3 4342             DbgLog(s1);
Q 4343             theprog.nOpType1 = OP_TMX;
df0321 4344             theprog.nParamCount = 1;
Q 4345             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4346             theprog.Params[0].nParamType = nCoilType;
4347             theprog.Params[0].nParamAddr = CoilAddr;
4348             theprog.Params[0].sParamStr = sCellNameA;
418cb3 4349             progsec.Append(theprog);
e55aec 4350             sProgSec.AppendFormat(_T("TM %s %d %s\r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
418cb3 4351             nSteps += 1;
e55aec 4352             nNextX = 3;
ad1b4b 4353         }
e55aec 4354         else if (nType == typeFN1)
ad1b4b 4355         {
e55aec 4356             s1.Format(_T("%d %d FN1 %s %s"), nCurPosY, nCurPosX, sCellName, Cells[nCurPosY][nCurPosX + 1].sParam);
418cb3 4357             DbgLog(s1);
Q 4358             theprog.nOpType1 = OP_INC;
4359             progsec.Append(theprog);
4360             sProgSec.AppendFormat(_T("FN1 %s %s\r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam);
4361             nSteps += 1;
e55aec 4362             nNextX = 2;
ad1b4b 4363         }
e55aec 4364         else if (nType == typeFN2)
ad1b4b 4365         {
418cb3 4366             s1.Format(_T("%d %d FN2 %s %s %s "), nCurPosY, nCurPosX, sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
Q 4367             DbgLog(s1);
4368             theprog.nOpType1 = OP_MV;
4369             progsec.Append(theprog);
4370             sProgSec.AppendFormat(_T("FN2 %s %s %s \r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
4371             nSteps += 1;
e55aec 4372             nNextX = 3;
ad1b4b 4373         }
e55aec 4374         else if (nType == typeFN3)
ad1b4b 4375         {
418cb3 4376             s1.Format(_T("%d %d FN3 %s %s %s %s"), nCurPosY, nCurPosX, sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam, Cells[nCurPosY][nCurPosX + 3].sParam);
Q 4377             DbgLog(s1);
4378             theprog.nOpType1 = OP_ADD3;
4379             progsec.Append(theprog);
4380             sProgSec.AppendFormat(_T("FN3 %s %s %s %s\r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam, Cells[nCurPosY][nCurPosX + 3].sParam);
4381             nSteps += 1;
e55aec 4382             nNextX = 4;
ad1b4b 4383         }
e55aec 4384         else
ad1b4b 4385         {
e55aec 4386             nNextX = 1;
418cb3 4387             //continue;
Q 4388         }
e55aec 4389         
Z 4390         #pragma endregion
4ed7fc 4391         */
418cb3 4392     }
Q 4393     return 0;
aac3b3 4394  }
4ed7fc 4395 //    记录y,x
4dfb88 4396
4ed7fc 4397 int CMTerm1View::ScanLDSCells2(int nStartLine, int nEndLine, int nPosY, int nPosX, int nSizeX,
Z 4398     int nLevel, stProgSection& progsec, CString& sProgSec, int& nSteps)
4399 {
4400     CString s1;
4401     int nCurPosX, nCurPosY;
4402     int nNextX = 0;//步长(到下个线圈起始位置应移动距离
4403     nCurPosY = nStartLine;
4404     nCurPosX = nPosX;
6ff05a 4405 //    int nCoilType, CoilAddr;
4ed7fc 4406     CMTerm1Doc* pDoc = GetDocument();
aac3b3 4407
4ed7fc 4408     for (int j = nPosX; j < nSizeX; j += nNextX)
Z 4409     {
4410         nCurPosX = j;
4411         //先处理当前单元;
4412         int nType = Cells[nCurPosY][nCurPosX].nType;
4413         CString sCellName = Cells[nCurPosY][nCurPosX].sCoilName;
4414         CMTerm1Doc::stProg theprog;
4415         CStringA sCellNameA;
4416         sCellNameA = sCellName;
4417         CString ProgSec;
4418         int theSteps = 0;
aac3b3 4419
4ed7fc 4420         stProgSection thisprogsec;
Z 4421
4422         //判断越界
89cd74 4423         if (j + nNextX > m_CellPerLine)
4ed7fc 4424         {
Z 4425             continue;
4426         }
4427         //if (!firstCoil && Cells[nCurPosY][j].bLeftLineUp)
4428         //{
4429         //    break;
4430         //}
4431         if (Cells[nCurPosY][nCurPosX].nType == typeNone)
4432         {
4433             nNextX = 1;
4434             continue;
4435         }
4436         //开始翻译单个单元格,并返回下个单元格位置
4437         nNextX = Translate2Prog(nType, nCurPosY, nCurPosX, sCellName, progsec, sProgSec, nSteps);
4438         //1.判断此单元格右侧一格是否有向下的竖线
4439         if (Cells[nCurPosY][j + nNextX].bLeftLineDn)
4440         {
4441             //1.1:有分支,直接开始读取下一行
4442             if (Cells[nCurPosY +1][j].nType == typeNone)
4443             {
4444                 if (Cells[nCurPosY + 1][j + nNextX].nType != typeNone)
4445                 {
4446                     firstCoil = true;
4447                 }
4448                 continue;
4449             }
4450
4451             firstCoil = true;
4452             ScanLDSCells2(nCurPosY + 1, nCurPosY + 1, nCurPosY + 1, 0, j + nNextX, ++nLevel, thisprogsec, ProgSec, theSteps);
4453             
4454             //有OR关系且不只一个节点
4455             if (theSteps > 1 && nLevel > 0)
4456             {
4457                 // 步数大于1,是复合结果,才使用ORS
4458                 s1.Format(_T("%d %d ORS "), nCurPosY, nCurPosX);
4459                 DbgLog(s1);
4460                 theprog.nOpType1 = OP_ORS;
4461                 //progsec.Append(theprog);
4462                 //sProgSec.AppendFormat(_T("ORS \r\n"));
4463                 thisprogsec.Append(theprog);
4464                 ProgSec.AppendFormat(_T("ORS \r\n"));
4465                 firstCoil = false;
4466                 nSteps += 1;
4467             }
4468
4469             //1.2:从后向前查找下一行是否还有向上的竖线(形成闭环)(ORS、ANS)
4470             for (int k = j; k >= 0; k--)
4471             {
4472                 if (Cells[nCurPosY + 1][k].nType == typeNone)
4473                 {
4474                     //如果遇到空格,还没搜到,就结束搜索
4475                     break;
4476                 }
4477                 if (Cells[nCurPosY+1][k].bLeftLineUp)
4478                 {
4479                     //如果有一条竖线,说明是形成了环,要用ANS
4480                     if (theSteps >= 1 && nLevel > 0)
4481                     {
4482                         //步数大于1,是复合结果,使用ANS
4483                         s1.Format(_T("%d %d ANS "), nCurPosY, nCurPosX);
4484                         DbgLog(s1);
4485                         theprog.nOpType1 = OP_ANS;
4486                         //progsec.Append(theprog);
4487                         //sProgSec.AppendFormat(_T("ANS \r\n"));
4488                         thisprogsec.Append(theprog);
4489                         ProgSec.AppendFormat(_T("ANS \r\n"));
4490                         nSteps += 1;
4491                     }
4492                 }
4493             }
4494             
4495             //将转换完成的部分加入到总集中
4496             nSteps += theSteps;
4497             progsec += thisprogsec;
4498             sProgSec += ProgSec;
4499             
4500             //1.3:查询此分支下一级连接点左右均存在节点,存在就PSHS
4501             if (Cells[nCurPosY + 1][j].nType != typeNone 
4502                 && Cells[nCurPosY + 1][j + 1].nType != typeNone)
4503             {
4504                 ++nPSHS;
4505                 CString push = _T("PSHS \r\n");
4506                 theprog.nOpType1 = OP_PSHS;
4507                 progsec.Append(theprog);
4508                 sProgSec.Append(push);
4509                 popsPoint[nPSHS] = std::make_pair(nCurPosY + 1, j + 1);
4510             }
4511         }//end  1.判断此单元格右侧一格是否有向下的竖线
4512
4513     }
4514     nLevel--;
4515     //已回到起始层
4516     if (nLevel == 0)
4517     {
4518         CMTerm1Doc::stProg theprog;
4519         for (int i = nPSHS; i >= 0; i--)
4520         {
4521             //+POP
4522             CString pop = _T("POPS \r\n");
4523             theprog.nOpType1 = OP_POPS;
4524             progsec.Append(theprog);
4525             sProgSec.Append(pop);
4526             //+fanyi
4527             //开始翻译单个单元格,并返回下个单元格位置
4528             //firstCoil = true;
4529             ScanLDSCells2(popsPoint[nPSHS].first, popsPoint[nPSHS].first, popsPoint[nPSHS].first, popsPoint[nPSHS].second, 16, nLevel, progsec, sProgSec, nSteps);
4530             nPSHS--;
4531
4532         }
4533         if (nPSHS == -1)
4534         {
4535             fill(popsPoint, popsPoint + 100, std::make_pair(0, 0));
4536         }
4537     }
4538
4539     return 0;
418cb3 4540 }
4ed7fc 4541
Z 4542
4543 int CMTerm1View::Translate2Prog(
4544     int nType, int nCurPosY, int nCurPosX, CString sCellName,
4545     stProgSection& progsec, CString& sProgSec, int& nSteps)
4546 {
4547     CString s1;
4548     int nNextX = 1;//步长
4549     int nCoilType, CoilAddr;
4550     CMTerm1Doc::stProg theprog;
4551     CMTerm1Doc* pDoc = GetDocument();
4552     CStringA sCellNameA;
4553     sCellNameA = sCellName;
4554     //if (nType == typeNone)
4555     //{
4556     //    return 0;
4557     //}
4558     if (nType == typeNO)
4559     {
4560         if (firstCoil && nType != typeLine1 && nType != typeLine2)
4561         {
4562             //先看往上面有没有连接
4563             if (Cells[nCurPosY][nCurPosX + nNextX].bLeftLineUp)
4564             {
4565                 // 往上面有连接,使用OR
4566                 sProgSec.AppendFormat(_T("OR %s\r\n"), sCellName);
4567                 theprog.nOpType1 = OP_OR;
4568             }
4569             else
4570             {
4571                 sProgSec.AppendFormat(_T("ST %s\r\n"), sCellName);
4572                 theprog.nOpType1 = OP_ST;
4573             }
4574             theprog.nParamCount = 1;
4575             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4576             theprog.Params[0].nParamType = nCoilType;
4577             theprog.Params[0].nParamAddr = CoilAddr;
4578             theprog.Params[0].sParamStr = sCellNameA;
4579             progsec.Append(theprog);
4580             firstCoil = false;
4581         }
4582         else
4583         {
4584             sProgSec.AppendFormat(_T("AN %s\r\n"), sCellName);
4585             theprog.nOpType1 = OP_AN;
4586             theprog.nParamCount = 1;
4587             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4588             theprog.Params[0].nParamType = nCoilType;
4589             theprog.Params[0].nParamAddr = CoilAddr;
4590             theprog.Params[0].sParamStr = sCellNameA;
4591             progsec.Append(theprog);
4592         }
4593
4594         nSteps += 1;
4595         nNextX = 1;
4596     }
4597     else if (nType == typeNC)
4598     {
4599         if (firstCoil && nType != typeLine1 && nType != typeLine2)
4600         {
4601             sProgSec.AppendFormat(_T("ST/ %s\r\n"), sCellName);
4602             theprog.nOpType1 = OP_ST_;
4603             theprog.nParamCount = 1;
4604             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4605             theprog.Params[0].nParamType = nCoilType;
4606             theprog.Params[0].nParamAddr = CoilAddr;
4607             theprog.Params[0].sParamStr = sCellNameA;
4608             progsec.Append(theprog);
4609             firstCoil = false;
4610         }
4611         else
4612         {
4613             sProgSec.AppendFormat(_T("AN/ %s\r\n"), sCellName);
4614             theprog.nOpType1 = OP_AN_;
4615             theprog.nParamCount = 1;
4616             pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4617             theprog.Params[0].nParamType = nCoilType;
4618             theprog.Params[0].nParamAddr = CoilAddr;
4619             theprog.Params[0].sParamStr = sCellNameA;
4620             progsec.Append(theprog);
4621         }
4622         nSteps += 1;
4623         nNextX = 1;
4624     }
4625     else if (nType == typePP)
4626     {
4627         //progsec.Append(theprog);
4628         sProgSec.AppendFormat(_T("PP %s\r\n"), sCellName);
4629         nSteps += 1;
4630         nNextX = 1;
4631     }
4632     else if (nType == typePN)
4633     {
4634         //progsec.Append(theprog);
4635         sProgSec.AppendFormat(_T("PN %s\r\n"), sCellName, sCellName);
4636         nSteps += 1;
4637         nNextX = 1;
4638     }
4639     else if (nType == typeNOT)
4640     {
4641         sProgSec.AppendFormat(_T("NOT %s\r\n"), sCellName);
4642         theprog.nOpType1 = OP_NOT;
4643         progsec.Append(theprog);
4644         nSteps += 1;
4645         nNextX = 1;
4646     }
4647     else if (nType == typeDF)
4648     {
4649         sProgSec.AppendFormat(_T("DF %s\r\n"), sCellName);
4650         theprog.nOpType1 = OP_DF;
4651         progsec.Append(theprog);
4652         nSteps += 1;
4653         nNextX = 1;
4654     }
4655     else if (nType == typeDF_)
4656     {
4657         sProgSec.AppendFormat(_T("DF/ %s\r\n"), sCellName);
4658         theprog.nOpType1 = OP_DF_;
4659         progsec.Append(theprog);
4660         nSteps += 1;
4661         nNextX = 1;
4662     }
4663     else if (nType == typeOUT)
4664     {
4665         sProgSec.AppendFormat(_T("OUT %s\r\n"), sCellName);
4666         theprog.nOpType1 = OP_OUT;
4667         theprog.nParamCount = 1;
4668         pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4669         theprog.Params[0].nParamType = nCoilType;
4670         theprog.Params[0].nParamAddr = CoilAddr;
4671         theprog.Params[0].sParamStr = sCellNameA;
4672         progsec.Append(theprog);
4673         nSteps += 1;
4674         nNextX = 1;
4675     }
4676     else if (nType == typeSET)
4677     {
4678         sProgSec.AppendFormat(_T("SET %s\r\n"), sCellName);
4679         theprog.nOpType1 = OP_SET;
4680         theprog.nParamCount = 1;
4681         pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4682         theprog.Params[0].nParamType = nCoilType;
4683         theprog.Params[0].nParamAddr = CoilAddr;
4684         theprog.Params[0].sParamStr = sCellNameA;
4685         progsec.Append(theprog);
4686         nSteps += 1;
4687         nNextX = 1;
4688     }
4689     else if (nType == typeRESET)
4690     {
4691         sProgSec.AppendFormat(_T("RESET %s\r\n"), sCellName);
4692         theprog.nOpType1 = OP_RESET;
4693         theprog.nParamCount = 1;
4694         pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4695         theprog.Params[0].nParamType = nCoilType;
4696         theprog.Params[0].nParamAddr = CoilAddr;
4697         theprog.Params[0].sParamStr = sCellNameA;
4698         progsec.Append(theprog);
4699         nSteps += 1;
4700         nNextX = 1;
4701     }
4702     else if (nType == typeCMP)
4703     {
4704         theprog.nOpType1 = OP_ST_GT;
4705         theprog.nParamCount = 1;
4706         progsec.Append(theprog);
4707         sProgSec.AppendFormat(_T("CMP %s %s %s \r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
4708         nSteps += 1;
4709         nNextX = 3;
4710     }
4711     else if (nType == typeTM)
4712     {
4713         theprog.nOpType1 = OP_TMX;
4714         theprog.nParamCount = 1;
4715         pDoc->TxtToCoilType(sCellNameA, &nCoilType, &CoilAddr);
4716         theprog.Params[0].nParamType = nCoilType;
4717         theprog.Params[0].nParamAddr = CoilAddr;
4718         theprog.Params[0].sParamStr = sCellNameA;
4719         progsec.Append(theprog);
4720         sProgSec.AppendFormat(_T("TM %s %d %s\r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
4721         nSteps += 1;
4722         nNextX = 3;
4723     }
4724     else if (nType == typeFN1)
4725     {
4726         theprog.nOpType1 = OP_INC;
4727         progsec.Append(theprog);
4728         sProgSec.AppendFormat(_T("FN1 %s %s\r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam);
4729         nSteps += 1;
4730         nNextX = 2;
4731     }
4732     else if (nType == typeFN2)
4733     {
4734         theprog.nOpType1 = OP_MV;
4735         progsec.Append(theprog);
4736         sProgSec.AppendFormat(_T("FN2 %s %s %s \r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam);
4737         nSteps += 1;
4738         nNextX = 3;
4739     }
4740     else if (nType == typeFN3)
4741     {
4742         theprog.nOpType1 = OP_ADD3;
4743         progsec.Append(theprog);
4744         sProgSec.AppendFormat(_T("FN3 %s %s %s %s\r\n"), sCellName, Cells[nCurPosY][nCurPosX + 1].sParam, Cells[nCurPosY][nCurPosX + 2].sParam, Cells[nCurPosY][nCurPosX + 3].sParam);
4745         nSteps += 1;
4746         nNextX = 4;
4747     }
4748     else
4749     {
4750         nNextX = 1;
4751         //continue;
4752     }
4753     return nNextX;
4754 }
4755
418cb3 4756
ad1b4b 4757 /// <summary>
Z 4758 /// 全部图形校验
4759 /// </summary>
4760 /// <returns></returns>
e55aec 4761 /// <remark>
Z 4762 /// 计划在第一个返回值中使用不同的错误代码代表不同的错误类型,
4763 /// 并在第二个返回值中填充错误提示信息
4764 /// </remark>
4ed7fc 4765  std::pair<int, CString> CMTerm1View::LDSCheckRule()
Z 4766  {
4767      CString message;
4768      int nDivCount = 0;
4769      int Divs[100] = { 0 };
4770      //以行为单位从上到下遍历(行遍历)
4771      for (int i = 0; i < m_nTotalRow; i++)
4772      {
4773          int nRow = i;
4774          int bConnected = 0;
4775          bool checkFlag = false;//0列检验结果
ad1b4b 4776
4ed7fc 4777          //本行的0列检查
Z 4778          if (Cells[nRow][0].nType == 0)
4779          {
4780              checkFlag = true;
4781          }
ad1b4b 4782
4ed7fc 4783          //遍历此行的1-15列(确定单元格)
Z 4784          for (int j = 1; j < m_CellPerLine; j++)
4785          {
4786              int nCol = j;
4787              //如果0列为空
4788              if (checkFlag)
4789              {
4790                  //有左侧上竖线
4791                  if (Cells[nRow][nCol].bLeftLineUp)
4792                  {
4793                      //如果上层为空单元格,无效竖线,直接删除-----可以单独判断
4794                      if (nRow - 1 >= 0 && Cells[nRow - 1][nCol].nType == 0)
4795                      {
4796                          //清理单元格
4797                          Cells[nRow][nCol].clear();
4798                      }
4799                      //如果是none,错误:短路或回路
4800                      else if (Cells[nRow][nCol].nType == 0)
4801                      {
4802                          message.Format(_T("((%d,%d) 附近位置产生触点短路或回路!"), nRow, nCol);
4803                          return std::make_pair(111, message);
4804                      }
4805                      //如果不为none。可以转换,但是提示:无法绘制图形(程序不合理)
4806                      if (Cells[nRow][nCol].nType != 1)
4807                      {
4808                          message.Format(_T("((%d,%d) 无法绘制图形(程序不合理)"), nRow, nCol);
4809                          return std::make_pair(111, message);
4810                      }
ad1b4b 4811
4ed7fc 4812                  }
Z 4813                  //没有左侧上竖线,且此单元格类型 不为空或线
4814                  else if (Cells[nRow][nCol].nType > 2)
4815                  {
4816                      //此单元格为单独的线圈或指令单元,需要触点输入
4817                      message.Format(_T("((%d,%d) 需要触点输入"), nRow, nCol);
4818                      return std::make_pair(111, message);
4819                  }
4820                  //有左侧下竖线,且此单元格类型为空
4821                  if (Cells[nRow][nCol].bLeftLineDn)
4822                  {
4823                      //不支持回路
4824                  }
4825              }
4826              //如0列非空
4827              else
4828              {
ad1b4b 4829
4ed7fc 4830              }
Z 4831          }
ad1b4b 4832
e55aec 4833
4ed7fc 4834      }
Z 4835      return std::make_pair(0, message);
4836  }