2013 Nov: Reversing MACD: The Sequel by Johnny Dough

ICE Data Services -

PMACD_Signal.efs  

EFSLibrary - Discussion Board  

File Name: PMACD_Signal.efs

Description:
Reversing MACD: The Sequel by Johnny Dough

Formula Parameters:

PMACD_Signal.efs

  • Price Source: Close
  • Period Fast: 12
  • Period Slow: 26
  • Period Signal: 9
  • MA type: EMA
  • Plot computed price shift forward by 1: true

Notes:
The related article is copyrighted material. If you are not a subscriber of Stocks & Commodities, please visit www.traders.com.

Download File:
PMACD_Signal.efs


PMACD_Signal.efs

EFS Code:
PMACD_Signal.efs

/*********************************
Provided By:  
    Interactive Data Corporation (Copyright © 2013) 
    All rights reserved. This sample eSignal Formula Script (EFS)
    is for educational purposes only. Interactive Data Corporation
    reserves the right to modify and overwrite this EFS file with 
    each new release. 

Description:        
    Reversing MACD: The Sequel
    
Version:            1.00  11/11/2013

Formula Parameters:                        Default:
Price Source                               Close
Period Fast                                12
Period Slow                                26
Period Signal                              9
MA type                                    EMA
Plot computed price shift forward by 1     true

Notes:
    The related article is copyrighted material. If you are not a subscriber
    of Stocks & Commodities, please visit www.traders.com.

**********************************/

var fpArray = new Array();

function preMain()
{      
    setPriceStudy(true);
    setStudyTitle("Reversing MACD: The Sequel");
        
    setDefaultBarFgColor(Color.green, 0);
    setDefaultBarFgColor(Color.blue, 1);
    setDefaultBarFgColor(Color.red, 2);
         
    var x=0;
    
    fpArray[x] = new FunctionParameter("fpPriceSource", FunctionParameter.STRING);
    with(fpArray[x++])
    {
        setName("Price Source");
        addOption("Open");
        addOption("Close");
        addOption("Low");
        addOption("High");
        addOption("HLC/3");
        setDefault("Close");
    }
 
    fpArray[x] = new FunctionParameter("fpFast", FunctionParameter.NUMBER);
    with(fpArray[x++])
    {
        setName("Period Fast");
        setLowerLimit(1);
        setUpperLimit(50);
        setDefault(12);
    }
    
    fpArray[x] = new FunctionParameter("fpSlow", FunctionParameter.NUMBER);
    with(fpArray[x++])
    {
        setName("Period Slow");
        setLowerLimit(2);
        setUpperLimit(50);
        setDefault(26);
    }
    
    fpArray[x] = new FunctionParameter("fpSignal", FunctionParameter.NUMBER);
    with(fpArray[x++])
    {
        setName("Period Signal");
        setLowerLimit(0);
        setUpperLimit(50);
        setDefault(9);
    }
    
    fpArray[x] = new FunctionParameter("fpMAtype", FunctionParameter.STRING);
    with(fpArray[x++])
    {
        setName("MA type");
        addOption("EMA");
        addOption("SMA");
        setDefault("EMA");      
    }

    fpArray[x] = new FunctionParameter("fpShift", FunctionParameter.BOOLEAN);
    with(fpArray[x++])
    {
        setName("Plot computed price shift forward by 1");
        setDefault(true);    
    }  
}

var bInit = false;
var bVersion = null;

var xEq = null;
var xZero = null;
var xSignal = null;

function main(fpPriceSource, fpFast, fpSlow, fpSignal, fpMAtype, fpShift)
{
    if (bVersion == null) bVersion = verify();
    if (bVersion == false) return;

    var nShift = null;
    var xSource = null;
    
    if (!fpShift) nShift = 0
    else nShift = -1;
     
    if(!bInit)
    {
        switch (fpPriceSource)
        {
            case "Open": 
                xSource = open();
                break;
            case "Close":
                xSource = close();
                break;
            case "High":
                xSource = high();
                break;
            case "Low":
                xSource = low();
                break;
            case "HLC/3":
                xSource = hlc3();
                break;
            default : return;
        }

        switch (fpMAtype)
        {
            case "SMA":
                NameAverage_Eq = "PsMACDeq";
                NameAverage_Zero = "PsMACDzero";
                NameAverage_Signal = "PsMACDsignal";        
                break;
            case "EMA":
                NameAverage_Eq = "PMACDeq";
                NameAverage_Zero = "PMACDzero";
                NameAverage_Signal = "PMACDsignal";
                break;
            default : return;
        }
       
        xEq = efsInternal(NameAverage_Eq, fpFast, fpSlow, xSource);
        xZero = efsInternal(NameAverage_Zero, fpFast, fpSlow, xSource);
        xSignal = efsInternal(NameAverage_Signal, fpFast, fpSlow, fpSignal, xSource)

        setCursorLabelName(NameAverage_Eq, 0);
        setCursorLabelName(NameAverage_Zero, 1);
        setCursorLabelName(NameAverage_Signal, 2);
              
        bInit = true;
    }

    var nEq = xEq.getValue(nShift);
    var nZero = xZero.getValue(nShift);
    var nSignal = xSignal.getValue(nShift);
  
    if (nEq == null || nZero == null || nSignal == null)
        return;

    return [nEq, nZero, nSignal]
}

var xEMAx = null;
var xEMAy = null;

function Calc_ValueEMA(nPeriodX, nPeriodY, xSeries)
{    
    if (getBarState() == BARSTATE_ALLBARS)
    {
        xEMAx = ema(nPeriodX, xSeries);
        xEMAy = ema(nPeriodY, xSeries);
    }

    var nEMAx = xEMAx.getValue(0);
    var nEMAy = xEMAy.getValue(0);  
    
    if (nEMAx == null || nEMAy == null)
        return;

    var nAlphaX = 2 / (1 + nPeriodX);
    var nAlphaY = 2 / (1 + nPeriodY);
 
    return new Array(nEMAx, nEMAy, nAlphaX, nAlphaY);
}

function PMACDeq(nPeriodX, nPeriodY, xSeries)
{    
    var nReturnValue = null;
    var aValueArray = Calc_ValueEMA(nPeriodX, nPeriodY, xSeries);
   
    if (aValueArray != null)
    {
        var nEMAx = aValueArray[0];
        var nEMAy = aValueArray[1];
        var nAlphaX = aValueArray[2];
        var nAlphaY = aValueArray[3];

        nReturnValue = (nAlphaX * nEMAx - nAlphaY * nEMAy) / (nAlphaX - nAlphaY);
    }  
    
    return nReturnValue;
}

function PMACDlevel(nPeriodX, nPeriodY, nLevel, xSeries)
{
    var nReturnValue = null;
    var aValueArray = Calc_ValueEMA(nPeriodX, nPeriodY, xSeries);
   
    if (aValueArray != null)
    {
        var nEMAx = aValueArray[0];
        var nEMAy = aValueArray[1];
        var nAlphaX = aValueArray[2];
        var nAlphaY = aValueArray[3];

        nReturnValue = (nLevel + (1 - nAlphaY) * nEMAy - (1 - nAlphaX) * nEMAx) / (nAlphaX - nAlphaY);
    }  
   
    return nReturnValue;
}

var xEMAx = null;
var xEMAy = null;
var xMACDValue = null;
var xMACDSignal = null;

function PMACDsignal(nPeriodX, nPeriodY, nPeriodZ, xSeries)
{
    if (getBarState() == BARSTATE_ALLBARS)
    {
        xEMAx = ema(nPeriodX, xSeries);
        xEMAy = ema(nPeriodY, xSeries);
        xMACDValue = efsInternal("Calc_MACDValue", xEMAx, xEMAy);
        xMACDSignal = ema(nPeriodZ, xMACDValue);
    }

    var nReturnValue = null;
    var aValueArray = Calc_ValueEMA(nPeriodX, nPeriodY, xSeries);
   
    if (aValueArray != null)
    {
        var nEMAx = aValueArray[0];
        var nEMAy = aValueArray[1];
        var nAlphaX = aValueArray[2];
        var nAlphaY = aValueArray[3];

        var nMACDSignal = xMACDSignal.getValue(0);
    
        if (nMACDSignal == null)
            return;
       
        nReturnValue = (nMACDSignal - nEMAx * (1 - nAlphaX) + nEMAy * (1 - nAlphaY)) / (nAlphaX - nAlphaY);
    }  
  
    return nReturnValue;
}

function Calc_MACDValue(xSeries1, xSeries2)
{
    var nValue1 = xSeries1.getValue(0);
    var nValue2 = xSeries2.getValue(0);
    
    if (nValue1 == null || nValue2 == null)
        return;
    
    var nReturnValue = nValue1 - nValue2;

    return nReturnValue;
}

function PMACDzero(nPeriodX, nPeriodY, xSeries)
{
    return PMACDlevel(nPeriodX, nPeriodY, 0, xSeries);
}

function PsMACDeq( nPeriodX, nPeriodY, xSeries)
{
    var nOffsetX = xSeries.getValue(1-nPeriodX); 
    var nOffsetY = xSeries.getValue(1-nPeriodY);

    if (nOffsetX == null || nOffsetY == null)
        return;

    var nReturnValue = (nPeriodX * nOffsetY - nPeriodY * nOffsetX) / (nPeriodX - nPeriodY);

    return nReturnValue;
}

var xSMAx_Zer = null;
var xSMAy_Zer = null;

function PsMACDzero( nPeriodX, nPeriodY, xSeries)
{
    if (getBarState() == BARSTATE_ALLBARS)
    {
        xSMAx_Zer = sma(nPeriodX, xSeries);
        xSMAy_Zer = sma(nPeriodY, xSeries);
    }
            
    var nSMAx = xSMAx_Zer.getValue(0);
    var nSMAy = xSMAy_Zer.getValue(0);
   
    var nOffsetX = xSeries.getValue(1-nPeriodX); 
    var nOffsetY = xSeries.getValue(1-nPeriodY);

    if (nSMAx == null || nSMAy == null || nOffsetX == null || nOffsetY == null)
        return;
    
    var nReturnValue = (nPeriodX * nPeriodY * (nSMAx - nSMAy) + nPeriodX * nOffsetY - nPeriodY * nOffsetX) / (nPeriodX - nPeriodY);
    
    return nReturnValue;
}

var xsMACD = null;
var xSMAsMACD = null;

function PsMACDsignal(nPeriodX, nPeriodY, nPeriodZ, xSeries)
{
    var nReturnValue = null;

    if (nPeriodZ != 1)
    {
        if (getBarState() == BARSTATE_ALLBARS)
        {
            xsMACD = efsInternal("Calc_sMACD", nPeriodX, nPeriodY, xSeries);
            xSMAsMACD = sma(nPeriodZ, xsMACD);
        }
               
        var nsMACD = xsMACD.getValue(0);
        var nSMAsMACD = xSMAsMACD.getValue(0);
       
        var nOffsetX = xSeries.getValue(1-nPeriodX); 
        var nOffsetY = xSeries.getValue(1-nPeriodY);
        var nOffsetZ = xsMACD.getValue(1-nPeriodZ); 

        if (nsMACD == null || nSMAsMACD == null || nOffsetX == null || nOffsetY == null || nOffsetZ == null)
            return;

        nReturnValue = (nsMACD * (nPeriodX * nPeriodY * nPeriodZ - nPeriodX * nPeriodY) -
                       nPeriodX * nPeriodY * nPeriodZ * nSMAsMACD - 
                       nOffsetX * (nPeriodY * nPeriodZ - nPeriodY) +
                       nOffsetY * (nPeriodX * nPeriodZ - nPeriodX) +
                       nPeriodX * nPeriodY * nOffsetZ) /
                       (nPeriodX * nPeriodZ - nPeriodY * nPeriodZ - nPeriodX + nPeriodY);
    }
    
    return nReturnValue;
}

var xSMAx_Sig = null;
var xSMAy_Sig = null;

function Calc_sMACD(nPeriodX, nPeriodY, xSeries)
{
    if (getBarState() == BARSTATE_ALLBARS)
    {
        xSMAx_Sig = sma(nPeriodX, xSeries);
        xSMAy_Sig = sma(nPeriodY, xSeries);
    }
   
    var nSMAx = xSMAx_Sig.getValue(0);
    var nSMAy = xSMAy_Sig.getValue(0);

    if (nSMAx == null || nSMAy == null)
        return;
 
    var nReturnValue = nSMAx - nSMAy;

    return nReturnValue;
}

function verify() 
{
    var b = false;
    if (getBuildNumber() < 779) {
        drawTextAbsolute(5, 35, "This study requires version 8.0 or later.", 
            Color.white, Color.blue, Text.RELATIVETOBOTTOM|Text.RELATIVETOLEFT|Text.BOLD|Text.LEFT,
            null, 13, "error");
        drawTextAbsolute(5, 20, "Click HERE to upgrade.@URL=http://www.esignal.com/download/default.asp", 
            Color.white, Color.blue, Text.RELATIVETOBOTTOM|Text.RELATIVETOLEFT|Text.BOLD|Text.LEFT,
            null, 13, "upgrade");
        return b;
    } else {
        b = true;
    }
    return b;
}