MS_Pentagon_001
Download scriptThis script is a specialized technical analysis tool designed for the MetaTrader platform. It combines geometric price action modeling with astronomical data to identify potential market structural points and historical significance.
Core Functionality
1. Geometric Price Structure (The "Pentagon" Logic) The primary purpose of this script is to identify and draw specific geometric patterns based on price movement. Rather than using standard lagging indicators, it monitors how the price interacts with established "break points."
- Dynamic Tracking: The tool tracks the market's trajectory by monitoring specific structural breaks (labeled as AB, AE, BC, DE, and CD). When the price crosses these designated thresholds, the script calculates the next geometric point in the sequence.
- Visual Mapping: Once a valid break is detected, the script automatically draws a five-pointed geometric shape (a pentagon) on your chart. These shapes represent the relationship between price points over specific time intervals.
- Automated Geometry: The system calculates the proportions of these shapes using mathematical constants (such as the Golden Ratio) to ensure that the visual representations are consistent with the script's internal logic.
2. Astronomical Event Integration A unique feature of this tool is its ability to overlay historical and future astronomical data onto the price chart.
- Eclipses: The script contains a pre-programmed database of Solar and Lunar eclipses.
- Visual Markers: When viewing the Daily (D1) timeframe, the script identifies these dates and places specific markers ("S" for Solar and "L" for Lunar) on the chart.
- Contextual Analysis: This allows traders to see historical price action in relation to significant celestial events, providing an additional layer of context for analysis.
3. Intelligent Data Management To keep the chart clean and functional, the script includes several background management features:
- Memory Stack: It maintains a "stack" of the most recent geometric points, ensuring that the tool only displays a manageable number of shapes (as defined by the user) rather than cluttering the entire history.
- Dynamic Time Shifting: The script includes a sophisticated time-calculation engine. This allows it to accurately project and locate price points across different timeframe intervals (from 1 minute up to monthly charts) while correctly accounting for leap years, varying month lengths, and daylight adjustments.
Summary of User Experience
For the user, this tool acts as an automated "geometric architect." It scans the market's history to find structural breaks, draws complex geometric shapes to visualize price flow, and highlights specific astronomical dates—all while automatically cleaning up old data to keep your workspace organized.
//+------------------------------------------------------------------+
//| Pentagon |
//+------------------------------------------------------------------+
#property copyright "*"
#property link "*"
#property indicator_chart_window
#property indicator_buffers 0
#property indicator_color1 Red
extern string EX_P_Bpoint="2008.03.17 00:00";
extern string EX_P_Dpoint="2008.08.15 00:00";
extern double EX_P_Epips=14000;
extern int EX_P_max=20;
extern int EX_P_Fwidth=3;
extern double EX_P_Fheight=0.03;
extern int EX_P_RSline=1; // Resistance support line
extern color EX_color1=Blue;
extern color EX_color2=Blue;
extern color EX_color3=Blue;
extern bool EX_show_astrology=true;
double h5;
datetime Tb,Td; int Xb,Xd;
int xsa,xsb,xsc,xsd,xse,xsf;
double ysa,ysb,ysc,ysd,yse,ysf;
datetime px; double py; int pd;
double pi=3.1415926535;
int pno=0,max_pno=20;
datetime ST_X[101]; int ST_D[101];
string solareclipse01="2005.04.09 00:00"; // The South Pacific
string solareclipse02="2005.10.03 00:00"; // Europe
string solareclipse03="2006.03.29 00:00"; // Africa
string solareclipse04="2006.09.22 00:00"; // Africa
string solareclipse05="2007.03.19 00:00"; // Alaska
string solareclipse06="2007.09.11 00:00"; // South America
string solareclipse07="2008.02.07 00:00"; // The South Pacific
string solareclipse08="2008.08.01 00:00"; // Russia
string solareclipse09="2009.01.26 00:00"; // India
string solareclipse10="2009.07.22 00:00"; // The South Pacific
string solareclipse11="2010.01.15 00:00"; // Africa
string solareclipse12="2010.07.11 00:00"; // Polynesia
string solareclipse13="2011.01.04 00:00"; // Europe
string solareclipse14="2011.06.02 00:00"; // Iceland
string solareclipse15="2011.11.25 00:00"; // Antarctica
string solareclipse16="2012.05.21 00:00"; // ú{
string solareclipse17="2012.11.14 00:00"; // Australia
string solareclipse18="2013.05.10 00:00"; //
string lunareclipse01="2005.10.17 00:00"; //
string lunareclipse02="2006.09.08 00:00"; //
string lunareclipse03="2007.03.04 00:00"; //
string lunareclipse04="2007.08.28 00:00"; //
string lunareclipse05="2008.08.17 00:00"; //
string lunareclipse06="2010.01.01 00:00"; //
string lunareclipse07="2010.06.26 00:00"; //
string lunareclipse08="2010.12.21 00:00"; //
string lunareclipse09="2011.06.11 00:00"; //
string lunareclipse10="2011.12.10 00:00"; //
string lunareclipse11="2012.06.04 00:00"; //
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{IndicatorShortName("Pentagon");
return(0);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
int deinit()
{DelObject();
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
int start()
{ int i,ic=IndicatorCounted(),fr,ix;
double ph;
if(ic==0)
{max_pno=EX_P_max; if(EX_P_max>100) max_pno=100;
Tb=StrToTime(EX_P_Bpoint);
Td=StrToTime(EX_P_Dpoint);
Xb=iBarShift(NULL,0,Tb);
Xd=iBarShift(NULL,0,Td);
if(EX_P_Epips==0.0) h5=MathAbs((Close[Xb]-Close[Xd])*1.5); else h5=EX_P_Epips*Point;
SetSize(Tb,Xb,Td,Xd);
px=Time[Xb+xsb];
if(Close[Xb]<Close[Xd]) {py=Close[Xb]+ysb; pd=1;} else {py=Close[Xb]-ysb; pd=-1;}
DrawPentagon(px,py,pd); PushST(px,pd);
if(Close[Xb]<Close[Xd]) ph=py-ysb; else ph=py+ysb;
DrawText("P00",Time[Xb-(xsc-xsb)/2],"High:"+DoubleToStr(h5,Digits)+","+DoubleToStr(xsc-xsb+1,0),ph,White);
}
if(ic==0) fr=Xb-1; else fr=Bars-ic;
for(i=fr; i>=0; i--)
{ix=iBarShift(NULL,0,px);
if(pd==1)
{if(ix>=i && i>ix-xsb && Close[i]<py-ysb*(ix-i)/xsb) // AB break
{px=Time[ix+xsc]; py=py-ysb; pd=-1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix>=i && i>ix-xse && Close[i]>py+yse*(ix-i)/xse) // AE break
{px=Time[ix+xse]; py=py+yse; pd=-1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix-xsb>=i && i>ix-xsc && Close[i]<py-ysb) // BC break
{px=Time[ix]; py=py-ysb*2.0; pd=-1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix-xse>=i && i>=ix-xsd && Close[i]>py+yse-yse*((ix-xse)-i)/(xsd-xse)) // DE break
{px=Time[ix-xse]; py=py+yse; pd=-1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix-xsc>=i && i>=ix-xsd && Close[i]<py-ysc+ysc*((ix-xsc)-i)/(xsd-xsc)) // CD break
{px=Time[ix-xsc]; py=py-ysc; pd=-1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
}
else
{if(ix>=i && i>ix-xsb && Close[i]>py+ysb*(ix-i)/xsb) // AB break
{px=Time[ix+xsc]; py=py+ysb; pd=1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix>=i && i>ix-xse && Close[i]<py-yse*(ix-i)/xse) // AE break
{px=Time[ix+xse]; py=py-yse; pd=1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix-xsb>=i && i>ix-xsc && Close[i]>py+ysb) // BC break
{px=Time[ix]; py=py+ysb*2.0; pd=1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix-xse>=i && i>=ix-xsd && Close[i]<py-yse+yse*((ix-xse)-i)/(xsd-xse)) // DE break
{px=Time[ix-xse]; py=py-yse; pd=1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
else if(ix-xsc>=i && i>=ix-xsd && Close[i]>py+ysc-ysc*((ix-xsc)-i)/(xsd-xsc)) // CD break
{px=Time[ix-xsc]; py=py+ysc; pd=1;
if(SearchST(px,pd)!=0) {DrawPentagon(px,py,pd); PushST(px,pd);}
}
}
}
if(Period()==PERIOD_D1 && EX_show_astrology) ProcEclipse();
return(0);
}
//+------------------------------------------------------------------+
//| SetSize |
//+------------------------------------------------------------------+
void SetSize(datetime tb,int xb,datetime td,int xd)
{
int x1=(xb-xd)*1.0/(0.618+(1-0.618)*1.0/2.0);
xsa=0;
xsb=x1*(1.0-0.618)*1.0/2.0;
xsc=x1-xsb;
xsd=x1;
xse=x1*1.0/2.0;
xsf=xse;
ysa=0.0;
ysb=h5*(1.0-(1.0-0.618)*1.0/2.0)*MathTan((pi/2.0)*36.0/90.0)/(0.618*1.0/2.0*MathTan((pi/2.0)*72.0/90.0));
ysc=ysb;
ysd=0.0;
yse=h5-ysb;
ysf=ysb-h5*(0.618*1.0/2.0*MathTan((pi/2.0)*(36.0+18.0)/90.0))/(0.618*1.0/2.0*MathTan((pi/2.0)*72.0/90.0));
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
int DrawPentagon(datetime x,double y,int direction)
{int wx=iBarShift(NULL,0,x);
datetime ta=x;
datetime tb=SiftXTime(wx,xsb);
datetime tc=SiftXTime(wx,xsc);
datetime td=SiftXTime(wx,xsd);
datetime te=SiftXTime(wx,xse);
datetime tf=te;
datetime tf1=SiftXTime(wx,xse-EX_P_Fwidth),tf2=SiftXTime(wx,xse+EX_P_Fwidth);
double pa=y;
double pb=y-ysb; if(direction==-1) pb=y+ysb;
double pc=y-ysc; if(direction==-1) pc=y+ysc;
double pd=y;
double pe=y+yse; if(direction==-1) pe=y-yse;
double pf=y-ysf; if(direction==-1) pf=y+ysf;
double pf1=pf+h5*EX_P_Fheight,pf2=pf-h5*EX_P_Fheight;
DrawTLine("P01"+pno,ta,pa,tb,pb,EX_color1,STYLE_SOLID,EX_P_RSline);
DrawTLine("P02"+pno,tb,pb,tc,pc,EX_color1,STYLE_SOLID,1);
DrawTLine("P03"+pno,tc,pc,td,pd,EX_color1,STYLE_SOLID,1);
DrawTLine("P04"+pno,td,pd,te,pe,EX_color1,STYLE_SOLID,1);
DrawTLine("P05"+pno,te,pe,ta,pa,EX_color1,STYLE_SOLID,EX_P_RSline);
DrawTLine("P06"+pno,ta,pa,tc,pc,EX_color2,STYLE_DOT,1);
DrawTLine("P07"+pno,tb,pb,td,pd,EX_color2,STYLE_DOT,1);
DrawTLine("P08"+pno,tc,pc,te,pe,EX_color2,STYLE_DOT,1);
DrawTLine("P09"+pno,td,pd,ta,pa,EX_color2,STYLE_DOT,1);
DrawTLine("P10"+pno,te,pe,tb,pb,EX_color2,STYLE_DOT,1);
DrawF(tf,pf1,tf1,pf,tf,pf2,tf2,pf,EX_color3);
pno++; pno=MathMod(pno,max_pno);
}
//+------------------------------------------------------------------+
//| DrawF |
//+------------------------------------------------------------------+
void DrawF(datetime t1,double p1,datetime t2,double p2,datetime t3,double p3,datetime t4,double p4,color cl) {
ObjectCreate("P11"+pno,OBJ_TRIANGLE,0,0,0,0,0,0,0);
ObjectSet("P11"+pno,OBJPROP_STYLE ,STYLE_SOLID);
ObjectSet("P11"+pno,OBJPROP_COLOR ,cl);
ObjectSet("P11"+pno,OBJPROP_WIDTH ,1);
ObjectSet("P11"+pno,OBJPROP_TIME1 ,t1);
ObjectSet("P11"+pno,OBJPROP_PRICE1,p1);
ObjectSet("P11"+pno,OBJPROP_TIME2 ,t2);
ObjectSet("P11"+pno,OBJPROP_PRICE2,p2);
ObjectSet("P11"+pno,OBJPROP_TIME3 ,t3);
ObjectSet("P11"+pno,OBJPROP_PRICE3,p3);
ObjectSet("P11"+pno,OBJPROP_RAY,false);
ObjectSet("P11"+pno,OBJPROP_BACK,true);
ObjectCreate("P12"+pno,OBJ_TRIANGLE,0,0,0,0,0,0,0);
ObjectSet("P12"+pno,OBJPROP_STYLE ,STYLE_SOLID);
ObjectSet("P12"+pno,OBJPROP_COLOR ,cl);
ObjectSet("P12"+pno,OBJPROP_WIDTH ,1);
ObjectSet("P12"+pno,OBJPROP_TIME1 ,t3);
ObjectSet("P12"+pno,OBJPROP_PRICE1,p3);
ObjectSet("P12"+pno,OBJPROP_TIME2 ,t4);
ObjectSet("P12"+pno,OBJPROP_PRICE2,p4);
ObjectSet("P12"+pno,OBJPROP_TIME3 ,t1);
ObjectSet("P12"+pno,OBJPROP_PRICE3,p1);
ObjectSet("P12"+pno,OBJPROP_RAY,false);
ObjectSet("P12"+pno,OBJPROP_BACK,true);
}
//+------------------------------------------------------------------+
//| PushSTACK |
//+------------------------------------------------------------------+
int PushST(datetime x,int d)
{ int i;
for(i=max_pno-1-1; i>=0; i--)
{ST_X[i+1]=ST_X[i]; ST_D[i+1]=ST_D[i];}
ST_X[0]=x; ST_D[0]=d;
return(0);
}
//+------------------------------------------------------------------+
//| SearchSTACK |
//+------------------------------------------------------------------+
int SearchST(datetime x,int d)
{ int rc,i;
rc=-1;
for(i=0; i<=max_pno-1 ;i++)
if(ST_X[i]==x && ST_D[i]==d) {rc=0; break;}
return(rc);
}
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
int DelObject()
{ int i;
ObjectDelete("P00");
for(i=0; i<=max_pno; i++)
{ObjectDelete("P01"+i); ObjectDelete("P02"+i); ObjectDelete("P03"+i);
ObjectDelete("P04"+i); ObjectDelete("P05"+i); ObjectDelete("P06"+i);
ObjectDelete("P07"+i); ObjectDelete("P08"+i); ObjectDelete("P09"+i);
ObjectDelete("P10"+i); ObjectDelete("P11"+i); ObjectDelete("P12"+i);
}
ObjectDelete("PS"+solareclipse01); ObjectDelete("PS"+solareclipse02); ObjectDelete("PS"+solareclipse03);
ObjectDelete("PS"+solareclipse04); ObjectDelete("PS"+solareclipse05); ObjectDelete("PS"+solareclipse06);
ObjectDelete("PS"+solareclipse07); ObjectDelete("PS"+solareclipse08); ObjectDelete("PS"+solareclipse09);
ObjectDelete("PS"+solareclipse10); ObjectDelete("PS"+solareclipse11); ObjectDelete("PS"+solareclipse12);
ObjectDelete("PS"+solareclipse13); ObjectDelete("PS"+solareclipse14); ObjectDelete("PS"+solareclipse15);
ObjectDelete("PS"+solareclipse16); ObjectDelete("PS"+solareclipse17); ObjectDelete("PS"+solareclipse18);
ObjectDelete("PL"+lunareclipse01); ObjectDelete("PL"+lunareclipse02); ObjectDelete("PL"+lunareclipse03);
ObjectDelete("PL"+lunareclipse04); ObjectDelete("PL"+lunareclipse05); ObjectDelete("PL"+lunareclipse06);
ObjectDelete("PL"+lunareclipse07); ObjectDelete("PL"+lunareclipse08); ObjectDelete("PL"+lunareclipse09);
ObjectDelete("PL"+lunareclipse10); ObjectDelete("PL"+lunareclipse11);
}
//+------------------------------------------------------------------+
//| ProcEclipse |
//+------------------------------------------------------------------+
void ProcEclipse()
{
SolarEclipse(solareclipse01);
SolarEclipse(solareclipse02);
SolarEclipse(solareclipse03);
SolarEclipse(solareclipse04);
SolarEclipse(solareclipse05);
SolarEclipse(solareclipse06);
SolarEclipse(solareclipse07);
SolarEclipse(solareclipse08);
SolarEclipse(solareclipse09);
SolarEclipse(solareclipse10);
SolarEclipse(solareclipse11);
SolarEclipse(solareclipse12);
SolarEclipse(solareclipse13);
SolarEclipse(solareclipse14);
SolarEclipse(solareclipse15);
SolarEclipse(solareclipse16);
SolarEclipse(solareclipse17);
SolarEclipse(solareclipse18);
LunarEclipse(lunareclipse01);
LunarEclipse(lunareclipse02);
LunarEclipse(lunareclipse03);
LunarEclipse(lunareclipse04);
LunarEclipse(lunareclipse05);
LunarEclipse(lunareclipse06);
LunarEclipse(lunareclipse07);
LunarEclipse(lunareclipse08);
LunarEclipse(lunareclipse09);
LunarEclipse(lunareclipse10);
LunarEclipse(lunareclipse11);
}
//+------------------------------------------------------------------+
//| SolarEclipse |
//+------------------------------------------------------------------+
int SolarEclipse(string tt)
{ int ib;
datetime dt=StrToTime(tt);
datetime bf=Time[Bars-1]; datetime bt=Time[0];
if(bf<=dt && dt<=bt)
{ib=iBarShift(NULL,0,dt);
DrawText("PS"+tt,dt,"S",High[ib]+(High[ib]-Low[ib])*1.5,HotPink);
}
else if(dt>Time[0]) DrawText("PS"+tt,dt,"S",Close[0],HotPink);
}
//+------------------------------------------------------------------+
//| LunarEclipse |
//+------------------------------------------------------------------+
int LunarEclipse(string tt)
{ int ib;
datetime dt=StrToTime(tt);
datetime bf=Time[Bars-1]; datetime bt=Time[0];
if(bf<=dt && dt<=bt)
{ib=iBarShift(NULL,0,dt);
DrawText("PL"+tt,dt,"L",Low[ib]-(High[ib]-Low[ib]),Aqua);
}
else if(dt>Time[0]) DrawText("PL"+tt,dt,"L",Close[0],Aqua);
}
//+------------------------------------------------------------------+
//| DrawTLine |
//+------------------------------------------------------------------+
void DrawTLine(string no,datetime t1,double p1,datetime t2,double p2,color cl,int st,int w)
{
if(ObjectFind(no)<0) ObjectCreate(no,OBJ_TREND,0,0,0,0,0);
ObjectSet(no,OBJPROP_STYLE ,st);
ObjectSet(no,OBJPROP_COLOR ,cl);
ObjectSet(no,OBJPROP_WIDTH ,w);
ObjectSet(no,OBJPROP_TIME1 ,t1);
ObjectSet(no,OBJPROP_PRICE1,p1);
ObjectSet(no,OBJPROP_TIME2 ,t2);
ObjectSet(no,OBJPROP_PRICE2,p2);
ObjectSet(no,OBJPROP_RAY,false);
ObjectSet(no,OBJPROP_BACK,false);
}
//+------------------------------------------------------------------+
//| DrawText |
//+------------------------------------------------------------------+
void DrawText(string no,datetime tb,string tx,double p,color cl)
{ ObjectCreate(no,OBJ_TEXT,0,0,0);
ObjectSet(no,OBJPROP_TIME1 ,tb);
ObjectSet(no,OBJPROP_PRICE1 ,p);
ObjectSet(no,OBJPROP_COLOR ,cl);
ObjectSet(no,OBJPROP_FONTSIZE,9);
ObjectSetText(no,tx);
}
//+------------------------------------------------------------------+
// SiftXTime |
//+------------------------------------------------------------------+
datetime SiftXTime(int x,int sf)
{ datetime dt;
if(x-sf>=0)
{dt=Time[x-sf];}
else
{dt=Timeshift(Time[0],sf-x);}
return(dt);
}
//+------------------------------------------------------------------+
// Timeshift |
//+------------------------------------------------------------------+
datetime Timeshift (datetime dt,int sf) {
int ty=TimeYear(dt);
int tm=TimeMonth(dt);
int td=TimeDay(dt);
int th=TimeHour(dt);
int ti=TimeMinute(dt);
int i;
for(i=1; i<=sf; i++)
{if (Period()==PERIOD_M1 ) ti=ti+1;
else if(Period()==PERIOD_M5 ) ti=ti+5;
else if(Period()==PERIOD_M15) ti=ti+15;
else if(Period()==PERIOD_M30) ti=ti+30;
else if(Period()==PERIOD_H1 ) th=th+1;
else if(Period()==PERIOD_H4 ) th=th+4;
else if(Period()==PERIOD_D1 ) td=td+1;
else if(Period()==PERIOD_W1 ) td=td+7;
else if(Period()==PERIOD_MN1) tm=tm+1;
if(ti>=60) {ti=ti-60; th++;}
if(th>=24) {th=th-24; td++;}
if(tm==1 || tm==3 || tm==5 || tm==7 || tm==8 || tm==10 || tm==12) {if(td>31) {tm++; td=td-31;}}
else if(tm==2) {
if(MathMod(ty,4)==0) // 09.11.03 update
{if(td>29) {tm++; td=td-29;}}
else
{if(td>28) {tm++; td=td-28;}}
}
else if(tm==4 || tm==6 || tm==9 || tm==11) if(td>30) {tm++; td=td-30;}
if(tm>12) {tm=1; ty++;}
}
return(StrToTime(ty+"."+tm+"."+td+" "+th+":"+ti));
}
Comments