RuleOf9 Kantor Basket

Download script
RuleOf9 Kantor Basket

This script functions as a comprehensive market analysis tool designed to track broad currency trends by monitoring a specific "basket" of eight major currency pairs. Instead of focusing on a single pair, it aggregates data to provide a more holistic view of market sentiment.

Core Logic and Functionality

1. Multi-Currency Basket Aggregation The indicator monitors the following eight pairs:

  • AUDUSD, EURUSD, GBPUSD, NZDUSD
  • AUDJPY, EURJPY, GBPJPY, NZDJPY

By combining these, the script attempts to filter out the "noise" of individual currency fluctuations and identify the underlying strength or weakness of major global currencies (specifically focusing on Australian, European, British, and New Zealand interests against the US Dollar and Japanese Yen).

2. Customizable Calculation Methods The tool offers three distinct ways to interpret price movement within this basket:

  • Method 0: Focuses on the difference between current openings and previous closes.
  • Method 1: Looks at the "Logical Trader" approach, measuring the distance between the close and open of the previous candle.
  • Method 2: Analyzes the immediate relationship between the current candle's close and the previous candle's open.

3. Data Processing and Smoothing Once the raw data from all eight pairs is gathered, the script performs several mathematical steps to make the information readable:

  • Summation: It totals the price movements over a user-defined period (defaulting to 30).
  • Binary Conversion: Depending on your settings, it can convert these complex numbers into simple directional signals (1 for up, -1 for down).
  • Smoothing: It applies a weighted formula to "smooth" out jagged price spikes, creating a clearer trend line that is easier for the human eye to follow.

4. Trend Tracking and Extremes The indicator identifies high and low boundaries based on historical data. It maps out the "Highest Sum" and "Lowest Sum" over an extended period, allowing you to see where current market momentum sits relative to recent extremes.

5. Automated Alerts The logic includes a specific "Rule of 9" trigger. It monitors how long the price remains in extreme zones (above 8 or below -8). If the trend persists at these extremes for a significant duration, the script will generate an automated alert on your platform, signaling a potential shift in the market trend.

Summary for the User

This tool is designed for traders who want to see the "big picture." Rather than watching one chart, you are watching a weighted summary of eight charts simultaneously. It simplifies complex multi-currency movements into a single smoothed line, highlighting whether the general market sentiment is bullish or bearish and alerting you when that momentum reaches an exhausted state.

Price Data Components
Series array that contains open prices of each barSeries array that contains close prices for each barSeries array that contains the highest prices of each barSeries array that contains the lowest prices of each bar
Miscellaneous
Implements a curve of type %1It issuies visual alerts to the screen
10 Views
0 Downloads
0 Favorites
RuleOf9 Kantor Basket
//+------------------------------------------------------------------+
//|                                        RuleOf9 Kantor Basket.mq4 |
//+------------------------------------------------------------------+
#property indicator_separate_window
#property indicator_buffers 4
#property indicator_color1 Yellow
#property indicator_color2 DodgerBlue
#property indicator_width2 2
#property indicator_color3 LimeGreen
#property indicator_color4 OrangeRed
//#property indicator_color5 Red
#property indicator_level1 0
#property indicator_level2 8
#property indicator_level3 -8

extern string TimeFrame_value = "TimeFrame(0,M5,M15,M30,H1,D1)";
extern string TimeFrame = "0";
extern int SumPeriod = 30;
extern string Sum_Mode = "0=Close-Open, 1=+1/-1";
extern int SumMode = 1;
extern string Day_Calculation_Type = "0=Brian,1=Logical Trader,2=Amibroker";
extern int Calculation_Type = 1;
extern int Smooth = 1;
//extern int MAPer = 8;

double P, PRU, PRD, R, D;

double LastValue[];
double HSum[];
double LSum[];
double SumValue[];

double dBuf3[];
int LastBar = -1;

double HCount[];
double LCount[];

double HigherTimeFrameValue[];
int timeFrame = 0;

int init() {

   IndicatorBuffers(4);

   SetIndexStyle(0,DRAW_LINE);
   SetIndexBuffer(0,LastValue);
   SetIndexLabel(0,"Price_C_O");
   SetIndexStyle(1,DRAW_HISTOGRAM);
   SetIndexBuffer(1,SumValue);
   SetIndexLabel(1,"C_O_Sum(" + SumPeriod + ")");
   SetIndexStyle(2,DRAW_LINE, STYLE_SOLID);
   SetIndexBuffer(2,HSum);
   SetIndexLabel(2,"Highest Sum");
   SetIndexStyle(3,DRAW_LINE, STYLE_SOLID);
   SetIndexBuffer(3,LSum);
   SetIndexLabel(3,"Lowest Sum");

   SetIndexStyle(4,DRAW_LINE, STYLE_SOLID);
   SetIndexBuffer(4,LSum);
   SetIndexLabel(4,"Lowest Sum");
/*   SetIndexStyle(5,DRAW_LINE);
   SetIndexBuffer(5,dBuf3);
   SetIndexLabel(5,"MA");*/
  
   IndicatorShortName("Rule of 9 Kantor Basket (" + Calculation_Type + "," + Smooth + ")");

   for(int idx=0; idx < SumPeriod; idx++) {

      SumValue[idx] = 0.0;
      HCount[idx] = 0.0;
      LCount[idx] = 0.0;
      HSum[idx] = 0.0;
      LSum[idx] = 0.0;
      LastValue[idx] = 0.0;

   }

   if (TimeFrame == "M5") {

      timeFrame = PERIOD_M5;

   } else if (TimeFrame == "M15") {

      timeFrame = PERIOD_M15;

   } else if (TimeFrame == "M30") {

      timeFrame = PERIOD_M30;

   } else if (TimeFrame == "H1") {

      timeFrame = PERIOD_H1;

   } else if (TimeFrame == "H4") {

      timeFrame = PERIOD_H4;

   } else if (TimeFrame == "D1") {

      timeFrame = PERIOD_D1;

   } else {

      timeFrame = 0;

   }

   LastBar = iTime(NULL, 0, 0);

   return(0);

}

int deinit() {

   return(0);

}

int start() {

   int i, l, EqAve, counted_bars = IndicatorCounted();
   int bar, limit;
   
   i = Bars - counted_bars - 1;
   double sum = 0;

   if (i < SumPeriod) {
   
      i = SumPeriod;
   
   }
   
   while (i >= 0) {

      if (iTime(NULL, timeFrame, i) != LastBar) {

         LastBar = iTime(NULL, timeFrame, i);
         sum = 0;

         if (Calculation_Type == 0 || (Calculation_Type != 1 && Calculation_Type != 2)) {
         
            D = (iOpen("AUDUSD", timeFrame, i) - iClose("AUDUSD", timeFrame, i+1))/MarketInfo("AUDUSD",MODE_POINT) +
                (iOpen("EURUSD", timeFrame, i) - iClose("EURUSD", timeFrame, i+1))/MarketInfo("EURUSD",MODE_POINT) +
                (iOpen("GBPUSD", timeFrame, i) - iClose("GBPUSD", timeFrame, i+1))/MarketInfo("GBPUSD",MODE_POINT) +
                (iOpen("NZDUSD", timeFrame, i) - iClose("NZDUSD", timeFrame, i+1))/MarketInfo("NZDUSD",MODE_POINT) +
                (iOpen("AUDJPY", timeFrame, i) - iClose("AUDJPY", timeFrame, i+1))/MarketInfo("AUDUSD",MODE_POINT) +
                (iOpen("EURJPY", timeFrame, i) - iClose("EURJPY", timeFrame, i+1))/MarketInfo("EURUSD",MODE_POINT) +
                (iOpen("GBPJPY", timeFrame, i) - iClose("GBPJPY", timeFrame, i+1))/MarketInfo("GBPUSD",MODE_POINT) +
                (iOpen("NZDJPY", timeFrame, i) - iClose("NZDJPY", timeFrame, i+1))/MarketInfo("NZDUSD",MODE_POINT);
            D = D/2;
            
         } else if (Calculation_Type == 1) {
         
            D = (iClose("AUDUSD", timeFrame, i+1) - iOpen("AUDUSD", timeFrame, i+1))/MarketInfo("AUDUSD",MODE_POINT) +
                (iClose("EURUSD", timeFrame, i+1) - iOpen("EURUSD", timeFrame, i+1))/MarketInfo("EURUSD",MODE_POINT) +
                (iClose("GBPUSD", timeFrame, i+1) - iOpen("GBPUSD", timeFrame, i+1))/MarketInfo("GBPUSD",MODE_POINT) +
                (iClose("NZDUSD", timeFrame, i+1) - iOpen("NZDUSD", timeFrame, i+1))/MarketInfo("NZDUSD",MODE_POINT) +
                (iClose("AUDJPY", timeFrame, i+1) - iOpen("AUDJPY", timeFrame, i+1))/MarketInfo("AUDJPY",MODE_POINT) +
                (iClose("EURJPY", timeFrame, i+1) - iOpen("EURJPY", timeFrame, i+1))/MarketInfo("EURJPY",MODE_POINT) +
                (iClose("GBPJPY", timeFrame, i+1) - iOpen("GBPJPY", timeFrame, i+1))/MarketInfo("GBPJPY",MODE_POINT) +
                (iClose("NZDJPY", timeFrame, i+1) - iOpen("NZDJPY", timeFrame, i+1))/MarketInfo("NZDJPY",MODE_POINT);
            D = D/2;
            
         } else if (Calculation_Type == 2) {
         
            D = (iClose("AUDUSD", timeFrame, i) - iOpen("AUDUSD", timeFrame, i+1))/MarketInfo("AUDUSD",MODE_POINT) +
                (iClose("EURUSD", timeFrame, i) - iOpen("EURUSD", timeFrame, i+1))/MarketInfo("EURUSD",MODE_POINT) +
                (iClose("GBPUSD", timeFrame, i) - iOpen("GBPUSD", timeFrame, i+1))/MarketInfo("GBPUSD",MODE_POINT) +
                (iClose("NZDUSD", timeFrame, i) - iOpen("NZDUSD", timeFrame, i+1))/MarketInfo("NZDUSD",MODE_POINT) +
                (iClose("AUDJPY", timeFrame, i) - iOpen("AUDJPY", timeFrame, i+1))/MarketInfo("AUDJPY",MODE_POINT) +
                (iClose("EURJPY", timeFrame, i) - iOpen("EURJPY", timeFrame, i+1))/MarketInfo("EURJPY",MODE_POINT) +
                (iClose("GBPJPY", timeFrame, i) - iOpen("GBPJPY", timeFrame, i+1))/MarketInfo("GBPJPY",MODE_POINT) +
                (iClose("NZDJPY", timeFrame, i) - iOpen("NZDJPY", timeFrame, i+1))/MarketInfo("NZDJPY",MODE_POINT);
            D = D/2;
            
         } /*else if (Calculation_Type == 3) {
            D = ((iClose("AUDUSD", timeFrame, i+1) - iOpen("AUDUSD", timeFrame, i+1))/MarketInfo("AUDUSD",MODE_POINT) +
                (iClose("EURUSD", timeFrame, i+1) - iOpen("EURUSD", timeFrame, i+1))/MarketInfo("EURUSD",MODE_POINT) +
                (iClose("GBPUSD", timeFrame, i+1) - iOpen("GBPUSD", timeFrame, i+1))/MarketInfo("GBPUSD",MODE_POINT) +
                (iClose("NZDUSD", timeFrame, i+1) - iOpen("NZDUSD", timeFrame, i+1))/MarketInfo("NZDUSD",MODE_POINT) +
                (iClose("AUDJPY", timeFrame, i+1) - iOpen("AUDJPY", timeFrame, i+1))/MarketInfo("AUDJPY",MODE_POINT) +
                (iClose("EURJPY", timeFrame, i+1) - iOpen("EURJPY", timeFrame, i+1))/MarketInfo("EURJPY",MODE_POINT) +
                (iClose("GBPJPY", timeFrame, i+1) - iOpen("GBPJPY", timeFrame, i+1))/MarketInfo("GBPJPY",MODE_POINT) +
                (iClose("NZDJPY", timeFrame, i+1) - iOpen("NZDJPY", timeFrame, i+1))/MarketInfo("NZDJPY",MODE_POINT)) +
                ((iClose("AUDUSD", timeFrame, i) - iOpen("AUDUSD", timeFrame, i+1))/MarketInfo("AUDUSD",MODE_POINT) +
                (iClose("EURUSD", timeFrame, i) - iOpen("EURUSD", timeFrame, i+1))/MarketInfo("EURUSD",MODE_POINT) +
                (iClose("GBPUSD", timeFrame, i) - iOpen("GBPUSD", timeFrame, i+1))/MarketInfo("GBPUSD",MODE_POINT) +
                (iClose("NZDUSD", timeFrame, i) - iOpen("NZDUSD", timeFrame, i+1))/MarketInfo("NZDUSD",MODE_POINT) +
                (iClose("AUDJPY", timeFrame, i) - iOpen("AUDJPY", timeFrame, i+1))/MarketInfo("AUDJPY",MODE_POINT) +
                (iClose("EURJPY", timeFrame, i) - iOpen("EURJPY", timeFrame, i+1))/MarketInfo("EURJPY",MODE_POINT) +
                (iClose("GBPJPY", timeFrame, i) - iOpen("GBPJPY", timeFrame, i+1))/MarketInfo("GBPJPY",MODE_POINT) +
                (iClose("NZDJPY", timeFrame, i) - iOpen("NZDJPY", timeFrame, i+1))/MarketInfo("NZDJPY",MODE_POINT));
             D = D/2;
         } */
         
/*         // Experiment of the logical trader book ACD signal
         P = (iHigh(NULL, PERIOD_D1, i+1) + iLow(NULL, PERIOD_D1, i+1) + iClose(NULL, PERIOD_D1, i+1)) / 3;
         R = (iHigh(NULL, PERIOD_D1, i+1) + iLow(NULL, PERIOD_D1, i+1)) / 2;
         PRU = P+(MathAbs(P-R));
         PRD = P-(MathAbs(P-R));

         if (iOpen(NULL, PERIOD_D1, i+1) <= PRU && iClose(NULL, PERIOD_D1, i+1) > PRU) {
      
            LastValueUp[i] = 2;
      
         } else if (iOpen(NULL, PERIOD_D1, i+1) >= PRD && iClose(NULL, PERIOD_D1, i+1) < PRD) {
      
            LastValueUp[i] = -2;
      
         } else {
      
            LastValueUp[i] = 0;
      
         }
*/

         if (SumMode == 0) {

            LastValue[i] = D;

         } else {

            if (D > 0) {

               LastValue[i] = 1;

            } else {

               LastValue[i] = -1;

            }
               
         
         }
         
         int period = 0;
         
         if (SumPeriod > ArraySize(LastValue)) {

            period = ArraySize(LastValue);

         } else {

            period = SumPeriod;

         }

         for(int idx=0; idx<period; idx++) {
      
            sum += LastValue[i+idx];

         }

         SumValue[i] = sum;
         if (Smooth == 1)
         {
            SumValue[i] = (SumValue[i]*4+SumValue[i+1]*2+SumValue[i+2]*2+SumValue[i+3])/9;
         }
                 
         HSum[i] = SumValue[ArrayMaximum(SumValue, SumPeriod*8, 0)];
         LSum[i] = SumValue[ArrayMinimum(SumValue, SumPeriod*8, 0)];

         if (SumValue[i] >= 8) {
         
            HCount[i] = HCount[i+1] + 1;
             
         } else {
         
            HCount[i] = 0.0;

         }
         if (SumValue[i] <= -8) {

            LCount[i] = LCount[i+1] + 1;

         } else {

            LCount[i] = 0.0;

         }
         
         if (LCount[i] <= -9 || HCount[i] >= 9) {
         
            Alert("Potential trend change on ", TimeToStr(Time[i], TIME_DATE));
         
         }
         
      }

      i--;

   }

   return(0);

}
//+------------------------------------------------------------------+

Comments