public override void ApplyTo(StockSerie stockSerie)
        {
            FloatSerie pukeSerie = new FloatSerie(stockSerie.Count);

             int period = ((int)this.parameters[0]);
             int smoothing = ((int)this.parameters[1]);
             int signalSmoothing = ((int)this.parameters[3]);
             int inputSmoothing = ((int)this.parameters[2]);

             FloatSerie closeSerie = stockSerie.GetSerie(StockDataType.CLOSE).CalculateEMA(inputSmoothing);

             var values = stockSerie.ValueArray;

             // Calculate PUKE
             for (int i = period; i < stockSerie.Count; i++)
             {

            int puke = 0;
            for (int j = i - period+1; j <= i; j++)
            {
               StockDailyValue dv = values[j];
               if (closeSerie[j] - closeSerie[j-1] >= 0) puke++;
               else  puke--;
            }
            pukeSerie[i] = puke;
             }

             pukeSerie = pukeSerie.CalculateEMA(smoothing);

             this.Series[0] = pukeSerie;
             this.series[0].Name = this.SerieNames[0];

             FloatSerie signalSerie = pukeSerie.CalculateEMA(signalSmoothing);
             this.series[1] = signalSerie;
             this.series[1].Name = this.SerieNames[1];

             // Detecting events
             this.CreateEventSeries(stockSerie.Count);

             for (int i = period; i < stockSerie.Count; i++)
             {
            this.eventSeries[0][i] = (signalSerie[i - 1] > pukeSerie[i - 1] && signalSerie[i] < pukeSerie[i]);
            this.eventSeries[1][i] = (signalSerie[i - 1] < pukeSerie[i - 1] && signalSerie[i] > pukeSerie[i]);
            this.eventSeries[2][i] = pukeSerie[i] > signalSerie[i];
            this.eventSeries[3][i] = pukeSerie[i] < signalSerie[i];
             }
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            // Set HLine value
             float trendThreshold = (float)this.Parameters[1];

             int period = (int)this.Parameters[0];
             FloatSerie atrSerie = stockSerie.GetIndicator("ATR(" + period + ")").Series[0];

             FloatSerie pDM = new FloatSerie(stockSerie.Count);
             FloatSerie mDM = new FloatSerie(stockSerie.Count);

             FloatSerie lowSerie = stockSerie.GetSerie(StockDataType.LOW).CalculateEMA((int)this.Parameters[2]);
             FloatSerie higherie = stockSerie.GetSerie(StockDataType.HIGH).CalculateEMA((int)this.Parameters[2]);

             // Calculate +DM and -DM
             for (int i = 1; i < stockSerie.Count; i++)
             {
            float rangeUp = higherie[i] - higherie[i - 1];
            float rangeDown = lowSerie[i - 1] - lowSerie[i];

            if (rangeUp > rangeDown)
            {
               pDM[i] = Math.Max(0, rangeUp);
            }
            else
            {
               mDM[i] = Math.Max(0, rangeDown);
            }
             }

             // Calclate +DI and -DI
             FloatSerie pDI = pDM.CalculateEMA(period).Div(atrSerie).Mult(100);
             FloatSerie mDI = mDM.CalculateEMA(period).Div(atrSerie).Mult(100);

             FloatSerie ADX = ((pDI - mDI).Abs() / (pDI + mDI)).CalculateEMA(period).Mult(100);

             ADX.Name = this.SerieNames[0];
             pDI.Name = this.SerieNames[1];
             mDI.Name = this.SerieNames[2];

             this.Series[0] = ADX;
             this.Series[1] = pDI;
             this.Series[2] = mDI;

             // Manage events
             this.CreateEventSeries(stockSerie.Count);

             for (int i = period; i < stockSerie.Count; i++)
             {
            this.eventSeries[0][i] = ADX[i] > trendThreshold && ADX[i] > ADX[i - 1] && pDI[i] > mDI[i];
            this.eventSeries[1][i] = ADX[i] > trendThreshold && ADX[i] > ADX[i - 1] && pDI[i] < mDI[i];
             }
        }
        public FloatSerie CalculateCorrelation(FloatSerie otherSerie, int period)
        {
            if (this.Count != otherSerie.Count)
            {
                return null;
            }
            FloatSerie correlationSerie = new FloatSerie(this.Count, "CORREL");
            float[] x = this.Values;
            float[] y = otherSerie.Values;
            float[] mx = this.CalculateEMA(period).Values;
            float[] my = otherSerie.CalculateEMA(period).Values;

            double sum1 = 0, sum2 = 0, sum3 = 0, xmx = 0, ymy = 0;
            correlationSerie[0] = 0;

            for (int i = 1; i < this.Count; i++)
            {
                sum1 = 0; sum2 = 0; sum3 = 0;
                for (int j = Math.Max(0, i - period); j <= i; j++)
                {
                    xmx = x[j] - mx[j];
                    ymy = y[j] - my[j];
                    sum1 += xmx * ymy;
                    sum2 += xmx * xmx;
                    sum3 += ymy * ymy;
                }

                correlationSerie[i] = (float)(sum1 / (Math.Sqrt(sum2) * Math.Sqrt(sum3)));
            }
            return correlationSerie;
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            FloatSerie highSerie = stockSerie.GetSerie(StockDataType.HIGH).CalculateEMA((int)this.Parameters[1]);
             FloatSerie lowSerie = stockSerie.GetSerie(StockDataType.LOW).CalculateEMA((int)this.Parameters[1]);
             FloatSerie closeSerie = stockSerie.GetSerie(StockDataType.CLOSE).CalculateEMA((int)this.Parameters[1]);

             FloatSerie atrSerie = new FloatSerie(stockSerie.Count);

             for (int i = 1; i < stockSerie.Count; i++)
             {
            atrSerie[i] = 100f*(highSerie[i] - lowSerie[i]) / closeSerie[i - 1];
             }

             this.series[0] = atrSerie.CalculateEMA((int)this.Parameters[0]);
             this.Series[0].Name = this.Name;
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            // Calculate Bollinger Bands
             FloatSerie breadthIndicator = new FloatSerie(stockSerie.Count);
             int fastSmoothing = (int)this.parameters[1];

             StockSerie breadthSerie = StockDictionary.StockDictionarySingleton[(string)this.parameters[0]];
             breadthSerie.Initialise();

             int index = -1;
             int i = 0;
             float breadth = 0;
             foreach (StockDailyValue dailyValue in stockSerie.Values)
             {
            if ((index = breadthSerie.IndexOf(dailyValue.DATE)) == -1)
            {
               breadthIndicator[i] = breadth;
            }
            else
            {
               breadthIndicator[i] = breadth = breadthSerie.ElementAt(index).Value.CLOSE;
            }
            i++;
             }

             breadthIndicator = breadthIndicator.CalculateEMA(fastSmoothing);

             this.series[0] = breadthIndicator;
             this.Series[0].Name = this.SerieNames[0];

             // Detecting events
             this.CreateEventSeries(stockSerie.Count);

             for (i = 1; i < stockSerie.Count; i++)
             {
            if (breadthIndicator[i] >= 0)
            {
               this.Events[0][i] = true;
            }
            else
            {
               this.Events[1][i] = true;
            }
            if (breadthIndicator[i] >= breadthIndicator[i - 1])
            {
               this.Events[2][i] = true;
            }
            else
            {
               this.Events[3][i] = true;
            }
             }
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            int period = (int)this.parameters[0];
             int smooting = (int)this.parameters[1];
             int signalSmoothing = (int)this.parameters[2];

             FloatSerie closeSerie = stockSerie.GetSerie(StockDataType.CLOSE);
             if (smooting > 1) closeSerie = closeSerie.CalculateEMA(smooting);

             FloatSerie momentumSerie = new FloatSerie(stockSerie.Count);
             for (int i = period; i < stockSerie.Count; i++)
             {
            momentumSerie[i] = 100.0f * (closeSerie[i] - closeSerie[i - period]) / closeSerie[i - period];
             }

             FloatSerie signalSerie = momentumSerie.CalculateEMA(signalSmoothing);

             this.series[0] = momentumSerie;
             this.series[0].Name = this.SerieNames[0];

             this.series[1] = signalSerie;
             this.series[1].Name = this.SerieNames[1];

             // Detecting events
             this.CreateEventSeries(stockSerie.Count);

             FloatSerie atrSerie = 100.0f * stockSerie.GetSerie(StockDataType.ATR).CalculateEMA(smooting) / closeSerie;

             for (int i = 2; i < stockSerie.Count; i++)
             {
            this.eventSeries[0][i] = (momentumSerie[i] - signalSerie[i]) >= atrSerie[i];
            this.eventSeries[1][i] = (momentumSerie[i] - signalSerie[i]) <= -atrSerie[i];
            this.eventSeries[2][i] = this.eventSeries[0][i] && !this.eventSeries[0][i - 1];
            this.eventSeries[3][i] = this.eventSeries[1][i] && !this.eventSeries[1][i - 1];
             }
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            FloatSerie fastK = stockSerie.CalculateFastOscillator((int)this.parameters[0]).Div(100.0f).Sub(0.5f);

             FloatSerie oscSerie = new FloatSerie(stockSerie.Count);

             int i = 0;
             StockDailyValue previousValue = null;
             float previousOSCValue = 0.0f;
             foreach (StockDailyValue dailyValue in stockSerie.Values)
             {
            if (previousValue != null)
            {
               if (fastK[i] > 0)
               {
                  previousOSCValue += (1.0f - previousOSCValue) * fastK[i];
               }
               else
               {
                  previousOSCValue -= (-1.0f - previousOSCValue) * fastK[i];
               }

               oscSerie[i] = previousOSCValue;
            }
            previousValue = dailyValue;
            i++;

             }

             this.series[0] = oscSerie;
             this.Series[0].Name = this.Name;

             FloatSerie signalSerie = oscSerie.CalculateEMA((int)this.parameters[1]);
             this.series[1] = signalSerie;
             this.series[1].Name = this.series[0].Name + "_SIGNAL";

             // Detecting events
             this.CreateEventSeries(stockSerie.Count);
             for (i = 2; i < oscSerie.Count; i++)
             {
            this.eventSeries[0][i] = (oscSerie[i] > signalSerie[i]);
            this.eventSeries[1][i] = (oscSerie[i] < signalSerie[i]);
            this.eventSeries[0][i] = eventSeries[0][i] & !eventSeries[0][i - 1];
            this.eventSeries[1][i] = eventSeries[1][i] & !eventSeries[1][i - 1];
             }
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            FloatSerie highSerie = stockSerie.GetSerie(StockDataType.HIGH);
             FloatSerie lowSerie = stockSerie.GetSerie(StockDataType.LOW);

             FloatSerie chopSerie = new FloatSerie(stockSerie.Count);
             int period = (int) this.parameters[0];

             for (int i = period; i < stockSerie.Count; i++)
             {
            float low = float.MaxValue;
            float high = float.MinValue;
            float dist = 0f;
            for (int j = i - period; j <= i; j++)
            {
               low = Math.Min(low, lowSerie[j]);
               high = Math.Max(high, highSerie[j]);
               dist += highSerie[j] - lowSerie[j];
            }
            chopSerie[i] = dist/(high - low);
             }
             chopSerie = chopSerie.CalculateEMA((int) this.parameters[1]);
             this.series[0] = chopSerie;
             this.series[0].Name = this.Name;

             FloatSerie signal = chopSerie.CalculateEMA((int)this.parameters[1]);
             this.series[1] = signal;
             this.series[1].Name = this.SerieNames[1];

             // Detecting events
             this.CreateEventSeries(stockSerie.Count);

             for (int i = 1; i < stockSerie.Count; i++)
             {
            this.eventSeries[0][i] = chopSerie[i] >= signal[i];
            this.eventSeries[1][i] = chopSerie[i] < signal[i];
            this.eventSeries[2][i] = (chopSerie[i - 1] < signal[i - 1] && chopSerie[i] >= signal[i]);
            this.eventSeries[3][i] = (chopSerie[i - 1] >= signal[i - 1] && chopSerie[i] < signal[i]);
             }
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            StockDailyValue previousValue = null;
             FloatSerie varSerie = new FloatSerie(stockSerie.Count);
             FloatSerie varAbsSerie = new FloatSerie(stockSerie.Count);
             int i = 0;
             float var = 0;
             foreach (StockDailyValue value in stockSerie.Values)
             {
            if (previousValue != null)
            {
               var = (value.CLOSE - previousValue.CLOSE)/previousValue.CLOSE;
               varSerie[i] = var;
               varAbsSerie[i] = Math.Abs(var);
            }
            else
            {
               varSerie[i] = 0;
               varAbsSerie[0] = 1;
            }
            previousValue = value;
            i++;
             }

             FloatSerie smoothedVarSerie = varSerie.CalculateEMA((int)this.parameters[0]).CalculateEMA((int)this.parameters[1]);
             FloatSerie smoothedVarAbsSerie = varAbsSerie.CalculateEMA((int)this.parameters[0]).CalculateEMA((int)this.parameters[1]);
             FloatSerie TSISerie = smoothedVarSerie / smoothedVarAbsSerie;

             this.series[0] = TSISerie;
             this.series[0].Name = this.SerieNames[0];
             this.series[1] = TSISerie.CalculateEMA((int)this.parameters[2]);
             this.series[1].Name = this.SerieNames[1];

             // Detecting events
             this.CreateEventSeries(stockSerie.Count);

             //
             float overbought = (float)this.Parameters[3];
             float oversold = (float)this.Parameters[4];
             for (i = (int)this.Parameters[1]; i < stockSerie.Count; i++)
             {
            float tsi = TSISerie[i];
            float signal = this.series[1][i];
            this.eventSeries[0][i] = (tsi >= overbought);
            this.eventSeries[1][i] = (tsi <= oversold);
            this.eventSeries[2][i] = (tsi > signal);
            this.eventSeries[3][i] = (tsi < signal);
             }
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            FloatSerie atrSerie = stockSerie.GetSerie(StockDataType.ATR).CalculateEMA((int)this.Parameters[0]);
             FloatSerie lowCloseSerie = new FloatSerie(stockSerie.Count);
             int i = 0;
             foreach (StockDailyValue dailyValue in stockSerie.Values)
             {
            lowCloseSerie[i++] = dailyValue.CLOSE - dailyValue.LOW;
             }
             lowCloseSerie = lowCloseSerie.CalculateEMA((int)this.Parameters[0]);
             lowCloseSerie = lowCloseSerie / atrSerie;
             lowCloseSerie = (lowCloseSerie * 100.0f) - 50.0f;

             this.series[0] = lowCloseSerie.CalculateEMA((int)this.Parameters[0] / 4);
             this.Series[0].Name = this.Name;
        }
        public override void ApplyTo(StockSerie stockSerie)
        {
            FloatSerie varSerie = new FloatSerie(stockSerie.Count);
            FloatSerie emaSerie = varSerie.CalculateEMA((int)this.parameters[0]);

            int period = (int)this.parameters[0];
            for (int i = period; i < stockSerie.Count; i++)
            {
                float close1 = stockSerie.ValueArray[i - period].CLOSE;
                float close2 = stockSerie.ValueArray[i].CLOSE;
                float var = 0;
                if (close2 < close1)
                {
                    var = (close2 - close1) / close1;
                }
                else
                {
                    close2 = 1f / close2;
                    close1 = 1f / close1;
                    var = -(close2 - close1) / close1;
                }
                varSerie[i] = var*100f;
            }

            this.series[0] = varSerie;
            this.Series[0].Name = this.Name;
        }