EA-Setka-2/Libs/MQL5Trace/View/TraceView.mqh

279 lines
25 KiB
MQL5
Raw Permalink Normal View History

2025-05-30 14:50:44 +02:00
<EFBFBD><EFBFBD>//+------------------------------------------------------------------+
//| TraceView |
//| Copyright 2006-2011, www.FXmaster.de |
//| www.FXmaster.de |
//+------------------------------------------------------------------+
#property copyright "Copyright 2006-2011, www.FXmaster.de"
#property link "www.FXmaster.de"
#property version "1.00"
#include "..\Trace.mqh"
#include "PropertyView.mqh"
//------------------------------------------------------------------ class CTreeView
class CTraceView: public CView
{
//--- 107>2K5 DC=:F88
public:
CTraceView() { }; // :>=AB@C:B>@
~CTraceView() { Deinit(); } // 45AB@CB>@
void Deinit(); // ?>;=0O 458=8F80;870F8O ?@54AB02;5=8O
virtual void Create(long chart); // A>7405< 8 0:B828@C5< ?@54AB02;5=85
//--- DC=:F88 >1@01>B:8 A>AB>O=8O
public:
int m_hagent; // E5=4;5@ 8=48:0B>@0-035=B0 4;O >B?@02:8 A>>1I5=89
CTraceCtrl* m_trace; // C:070B5;L =0 A>740==K5 B@59A5@
CTreeView* m_viewstack; // 45@52> 4;O >B>1@065=8O AB5:0
CPropertyView* m_viewprop; // 45@52> 4;O >B>1@065=8O A2>9AB2 C7;0
CTreeView* m_viewfile; // 45@52> 4;O >B>1@065=8O AB5:0 A 3@C??8@>2:>9 ?> D09;0<
CTreeView* m_viewclass; // 45@52> 4;O >B>1@065=8O AB5:0 A 3@C??8@>2:>9 ?> :;0AA0<
void OnTimer(); // >1@01>BG8: B09<5@0
void OnChartEvent(const int , const long& , const double& , const string& ); // >1@01>BG8: A>1KB8O
//--- DC=:F88 >B>1@065=8O
public:
virtual void Draw(); // >1=>28;8 >1J5:BK
virtual void DeleteView(); // C40;8;8 >B>1@065=85
void UpdateInfo(CNode *node, bool bclear); // 2K2>4 >:=0 ?>4@>1=>9 8=D>@<0F88 C7;0
string TimeSeparate(long time); // A?5FDC=:F8O 4;O ?@5>1@07>20=8O 2@5<5=8 2 AB@>:C
};
//------------------------------------------------------------------ ~CTraceView
void CTraceView::Deinit()
{ _IN("");
EventKillTimer();
delete m_viewclass;
delete m_viewfile;
delete m_viewprop;
delete m_viewstack;
ChartIndicatorDelete(m_chart, 0, "!TraceAgent");
m_hagent=INVALID_HANDLE;
ChartClose(m_chart);
}
//------------------------------------------------------------------ Create
void CTraceView::Create(long chart)
{ _IN("");
m_chart=ChartOpen(Symbol(), Period()); // >B:@K;8 >:=> G0@B0 4;O @01>BK
// ?@8:@5?8;8 : =5<C 035=B0 4;O >B?@02:8 A>>1I5=89 B5:CI5<C >:=C
#ifndef __MQL4__
m_hagent=iCustom(Symbol(), Period(), "!TraceAgent", chart);
if (m_hagent==INVALID_HANDLE) return;
ChartIndicatorAdd(m_chart, 0, m_hagent);
#endif
HideChart(m_chart, LightSteelBlue); // A:@K;8 >B>1@065=85 3@0D8:0 8 M;5<5=B>2
int heigh=(int)ChartGetInteger(m_chart, CHART_HEIGHT_IN_PIXELS)-m_dy-5; // 27O;8 ?0@0<5B@K G0@B0
int width=(int)ChartGetInteger(m_chart, CHART_WIDTH_IN_PIXELS)-10; // 27O;8 ?0@0<5B@K G0@B0
// A>7405< G5BK@5 45@520 4;O >B1@065=8O B@0AA8@>2:8 8 5Q 3@C??8@>2>:
double k=1.7, kx=width/(k+2);
int dh=int(heigh/2.5);
int x=5, y=m_dy+5, dx=int(k*kx);
// 3;02=K9 AB5:
m_viewstack=new CTreeView; m_viewstack.m_tree=m_trace.m_stack; // ?@8A>548=8;8 3@0D : >B>1@065=8N
m_viewstack.Create(m_chart, "viewstack", 0, Black, White, DarkBlue, x, y, dx, heigh-dh-3, 0, 8, "Tahoma"); // A>740;8 >1;0ABL
m_viewstack.m_tree.SortBy(TG_TEXT, true);
m_viewstack.Draw();
// 8=D>@<0F8O C7;0
m_viewprop=new CPropertyView; m_viewprop.m_tree=m_trace.m_prop; // ?@8A>548=8;8 3@0D : >B>1@065=8N
m_viewprop.Create(m_chart, "viewprop", 0, Black, White, DarkBlue, x, y+heigh-dh, dx, dh, 0, 8, "Tahoma"); // A>740;8 >1;0ABL
m_viewprop.Draw();
// 3@C??8@>2:0 ?> :;0AA0<
x+=dx+3; dx=(int)kx;
m_viewclass=new CTreeView; m_viewclass.m_tree=m_trace.m_class; // ?@8A>548=8;8 3@0D : >B>1@065=8N
m_viewclass.Create(m_chart, "viewclass", 0, Black, White, DarkBlue, x, y, dx, heigh, 0, 8, "Tahoma"); // A>740;8 >1;0ABL
m_viewclass.m_tree.SortBy(TG_TEXT, true);
m_viewclass.Draw();
// 3@C??8@>2:0 ?> D09;0<
x+=dx+3; dx=(int)kx;
m_viewfile=new CTreeView; m_viewfile.m_tree=m_trace.m_file; // ?@8A>548=8;8 3@0D : >B>1@065=8N
m_viewfile.Create(m_chart, "viewfile", 0, Black, White, DarkBlue, x, y, dx, heigh, 0, 8, "Tahoma"); // A>740;8 >1;0ABL
m_viewfile.m_tree.SortBy(TG_TEXT, true);
m_viewfile.Draw();
EventSetTimer(2);
ChartRedraw(m_chart);
}
//------------------------------------------------------------------ OnTimer
void CTraceView::OnTimer()
{ _IN("");
_WATCH("time", TTS(TimeLocal()));
Draw(); // ?5@5@8A>20;8 45@52LO
}
//------------------------------------------------------------------ OnChartEvent
void CTraceView::OnChartEvent(const int aid, const long& lparam, const double& dparam, const string& sparam)
{ _IN("");
if (aid<CHARTEVENT_CUSTOM) return; // @01>B05< B>;L:> A ?>;L7>20B5;LA:8<8 A>1KB8O<8
int id=aid-CHARTEVENT_CUSTOM;
_WATCH("Event", EnumToString(ENUM_CHART_EVENT(id)));
// 0=0;878@C5< :;8: =0 >1J5:B5
if (id==CHARTEVENT_OBJECT_CLICK)
{ _IN2("");
if (StringFind(sparam, "viewstack")>=0) // =0 3;02=>< AB5:5
{
int btn=m_viewstack.OnClick(sparam);
if (btn==BTN_CLEAR)
{
m_viewclass.DeleteView(); m_viewclass.m_tree.Clear(); m_viewclass.Draw();
m_viewfile.DeleteView(); m_viewfile.m_tree.Clear(); m_viewfile.Draw();
m_viewprop.DeleteView();
}
if (m_viewstack.m_sid<=0) return;
CNode *node=m_viewstack.m_tree.FindNode(m_viewstack.m_sid); if (NIL(node)) return;
UpdateInfo(node, true);
m_viewclass.m_tree.SelectBy(TG_ALL, NULL, false); m_viewclass.m_tree.CheckBy(TG_ALL, NULL, false);
m_viewclass.m_tree.SelectBy(TG_CLASS|TG_FUNC, node, true); m_viewclass.m_tree.CheckBy(TG_CLASS|TG_FUNC, node, true);
m_viewclass.m_sid=-1; m_viewclass.Draw();
m_viewfile.m_tree.SelectBy(TG_ALL, NULL, false); m_viewfile.m_tree.CheckBy(TG_ALL, NULL, false);
m_viewfile.m_tree.SelectBy(TG_FILE|TG_FUNC, node, true); m_viewfile.m_tree.CheckBy(TG_FILE|TG_FUNC, node, true);
m_viewfile.m_sid=-1; m_viewfile.Draw();
ChartRedraw(m_chart);
}
if (StringFind(sparam, "viewclass")>=0) // =0 45@525 :;0AA>2
{
int btn=m_viewclass.OnClick(sparam);
if (btn==BTN_CLEAR)
{
m_viewstack.m_tree.GroupBy(TG_CLASS, m_viewclass.m_tree); m_viewclass.m_tree.SortBy(TG_TEXT, true);
m_viewclass.Draw();
}
m_viewprop.DeleteView();
if (m_viewclass.m_sid<=0) return;
CNode *node=m_viewclass.m_tree.FindNode(m_viewclass.m_sid); if (NIL(node)) return;
m_viewstack.m_tree.SelectBy(TG_ALL, NULL, false); m_viewstack.m_tree.CheckBy(TG_ALL, NULL, false);
m_viewstack.m_tree.SelectBy(TG_CLASS|TG_FUNC, node, true); m_viewstack.m_tree.CheckBy(TG_CLASS|TG_FUNC, node, true);
m_viewstack.m_sid=-1; m_viewstack.Draw();
m_viewfile.m_tree.SelectBy(TG_ALL, NULL, false); m_viewfile.m_tree.CheckBy(TG_ALL, NULL, false);
m_viewfile.m_tree.SelectBy(TG_FILE|TG_FUNC, node, true); m_viewfile.m_tree.CheckBy(TG_FILE|TG_FUNC, node, true);
m_viewfile.m_sid=-1; m_viewfile.Draw();
ChartRedraw(m_chart);
}
if (StringFind(sparam, "viewfile")>=0) // =0 45@525 D09;>2
{
int btn=m_viewfile.OnClick(sparam);
if (btn==BTN_CLEAR)
{
m_viewstack.m_tree.GroupBy(TG_FILE, m_viewfile.m_tree); m_viewfile.m_tree.SortBy(TG_TEXT, true);
m_viewfile.Draw();
}
m_viewprop.DeleteView();
if (m_viewfile.m_sid<=0) return;
CNode *node=m_viewfile.m_tree.FindNode(m_viewfile.m_sid); if (NIL(node)) return;
m_viewstack.m_tree.SelectBy(TG_ALL, NULL, false); m_viewstack.m_tree.CheckBy(TG_ALL, NULL, false);
m_viewstack.m_tree.SelectBy(TG_FILE|TG_FUNC, node, true); m_viewstack.m_tree.CheckBy(TG_FILE|TG_FUNC, node, true);
m_viewstack.m_sid=-1; m_viewstack.Draw();
m_viewclass.m_tree.SelectBy(TG_ALL, NULL, false); m_viewclass.m_tree.CheckBy(TG_ALL, NULL, false);
m_viewclass.m_tree.SelectBy(TG_FILE|TG_FUNC, node, true); m_viewclass.m_tree.CheckBy(TG_FILE|TG_FUNC, node, true);
m_viewclass.m_sid=-1; m_viewclass.Draw();
ChartRedraw(m_chart);
}
if (StringFind(sparam, "viewprop")>=0) // =0 45@525 A2>9AB2 C7;0
{
m_viewprop.OnClick(sparam); ChartRedraw(m_chart);
}
}
if (id==CHARTEVENT_OBJECT_ENDEDIT)
{
if (StringFind(sparam, "viewprop")>=0) // =0 45@525 A2>9AB2 C7;0
{
if (StringFind(sparam, ".prop")>=0)
{
int n=(int)StringToInteger(ObjectGetString(m_chart, sparam, OBJPROP_TEXT)); // 27O;8
m_viewstack.m_tree.SetDataBy(TG_BRKUSE, m_viewstack.m_sid, n); // CAB0=>28;8
}
}
}
if (id==CHARTEVENT_CHART_CHANGE)
{
Draw(); // 87<5=8;AO @07<5@ >:=0 G0@B0
}
}
//------------------------------------------------------------------ Draw
void CTraceView::Draw()
{ _IN("");
int heigh=(int)ChartGetInteger(m_chart, CHART_HEIGHT_IN_PIXELS)-m_dy-5; // 27O;8 ?0@0<5B@K
int dh=int(heigh/2.5);
m_viewstack.m_dy=heigh-dh-3; m_viewprop.m_dy=dh; m_viewprop.m_y=m_viewstack.m_y+heigh-dh;
m_viewclass.m_dy=heigh; m_viewfile.m_dy=heigh;
int width=(int)ChartGetInteger(m_chart, CHART_WIDTH_IN_PIXELS)-10; // 27O;8 ?0@0<5B@K G0@B0
double k=1.7, kx=width/(k+2);
int x=5, dx=int(k*kx); m_viewstack.m_dx=dx; m_viewprop.m_dx=dx;
x+=dx+3; dx=int(kx); m_viewclass.m_x=x; m_viewclass.m_dx=dx;
x+=dx+3; dx=int(kx); m_viewfile.m_x=x; m_viewfile.m_dx=dx;
m_viewstack.Draw(); m_viewclass.Draw(); m_viewfile.Draw(); // ?5@5@8A>20;8 45@52LO
CNode *node=m_viewstack.m_tree.FindNode(m_viewstack.m_sid); // >B>1@0605< 8=D> ?> C7;C
UpdateInfo(node, false);
ChartRedraw(m_chart);
}
//------------------------------------------------------------------ Draw
void CTraceView::DeleteView()
{ _IN("");
m_viewstack.DeleteView(); m_viewprop.DeleteView();
m_viewclass.DeleteView(); m_viewfile.DeleteView(); // C40;8;8 >B>1@065=85
}
//------------------------------------------------------------------ UpdateInfo
void CTraceView::UpdateInfo(CNode *node, bool bclear)
{
if (NIL(node)) return;
if (NIL(m_viewprop.m_tree.m_root)) return;
//1. >?8@C5< =5:B>@K5 40==K5 C7;0 2 :>@=52>9 C75; 45@520, 4;O C?@>I5=8O >1@01>B:8 :=>?>:
CNode *root=m_viewprop.m_tree.m_root;
root.m_text=node.m_text; // =0720=85 C7;0
root.m_path=node.m_path; // 8<O D09;0
root.m_line=node.m_line; // =><5@ ;8=88 2 D09;5
int id, id2;
//2. !>7405< 45@52> ?> C7;C
id=m_viewprop.m_tree.AddNode(0, "Run-time 8=D>");
id2=m_viewprop.m_tree.AddNode(id, "'8A;> 2K7>2>2"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, string(node.m_uses));
id2=m_viewprop.m_tree.AddNode(id, "DebugBreak ?>A;5"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, node.m_brkuse<=0 ? "<>B:;>":string(node.m_brkuse));
m_viewprop.m_tree.SetDataBy(TG_EDIT, id2, true);
id2=m_viewprop.m_tree.AddNode(id, "!C<<0@=>5 2@5<O"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, TimeSeparate(node.m_tick));
id2=m_viewprop.m_tree.AddNode(id, ">A;54=89 2E>4"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, TTS(node.m_last));
id2=m_viewprop.m_tree.AddNode(id, ">?>;=8B5;L=>"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, node.m_desc);
id=m_viewprop.m_tree.AddNode(0, " 0A?>;>65=85");
id2=m_viewprop.m_tree.AddNode(id, "$09;"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, node.m_file);
id2=m_viewprop.m_tree.AddNode(id, "><5@ AB@>:8"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, string(node.m_line));
id2=m_viewprop.m_tree.AddNode(id, ";0AA"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, node.m_class);
id2=m_viewprop.m_tree.AddNode(id, "$C=:F8O"); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, node.m_func);
id=m_viewprop.m_tree.AddNode(0, "Watch-?0@0<5B@K");
if (bclear)
{
CNode *w=m_viewprop.m_tree.FindNode(id); // 27O;8 C75; watch
m_viewprop.DeleteView(w, false); // C40;8;8 53> >B>1@065=85
m_viewprop.m_tree.Clear(w); // C40;8;8 <0AA82 AC1C7;>2
}
// >B@8A>20;8 watch
int n=ArraySize(node.m_watch);
for (int i=0; i<n; i++)
{
id2=m_viewprop.m_tree.AddNode(id, node.m_watch[i].m_name); m_viewprop.m_tree.SetDataBy(TG_DESC, id2, node.m_watch[i].m_val);
}
m_viewprop.Draw();
}
//------------------------------------------------------------------ TimeSeparate
string CTraceView::TimeSeparate(long time)
{
long sec=1000; long min=sec*60; long hour=min*60; long day=hour*24;
string txt="";
long d=long(time/day); if (d>0) txt+=string(d)+" 4=59 ";
long h=long(time/hour)-d*day; if (h>9) txt+=string(h)+":"; else txt+="0"+string(h)+":";
long m=long(time/min)-(h*hour+d*day); if (m>9) txt+=string(m)+":"; else txt+="0"+string(m)+":";
long s=long(time/sec)-(m*min+h*hour+d*day); if (s>9) txt+=string(s)+"."; else txt+="0"+string(s)+".";
long ms=time-(s*sec+m*min+h*hour+d*day); txt+=string(ms);
return(txt);
}
#ifndef __MQL4__
extern CTraceView* m_traceview; // 548=AB25==K9 M:75<?;O@ 4;O >B>1@065=8O
#else
CTraceView* m_traceview; // 548=AB25==K9 M:75<?;O@ 4;O >B>1@065=8O
#endif