コード例 #1
0
ファイル: Ray.cs プロジェクト: HungryBear/rayden
 public Ray(IRay r)
 {
     this.Org = r.Origin;
     this.Dir = r.Direction;
     this.maxT = r.Max;
     this.minT = r.Min;
 }
コード例 #2
0
        public static IList<Point> GetIntersects(IRay line1, IRay line2)
        {
            IList<Point> list = new List<Point>();

            Point p1 = new Point(line1.Point.X, line1.Point.Y);
            Point p2 = new Point(line1.Point.X + line1.Vector.X, line1.Point.Y + line1.Vector.Y);

            Point q1 = new Point(line2.Point.X, line2.Point.Y);
            Point q2 = new Point(line2.Point.X + line2.Vector.X, line2.Point.Y + line2.Vector.Y);

            double x21 = p2.X - p1.X;
            double y21 = p2.Y - p1.Y;
            double x31 = q1.X - p1.X;
            double y31 = q1.Y - p1.Y;
            double x43 = q2.X - q1.X;
            double y43 = q2.Y - q1.Y;

            double paramDenominator = x43 * y21 - x21 * y43;

            double s = (x43 * y31 - x31 * y43) / paramDenominator;

            double x = p1.X + (p2.X - p1.X) * s;
            double y = p1.Y + (p2.Y - p1.Y) * s;

            list.Add(new Point(x, y));

            return list;
        }
コード例 #3
0
ファイル: IUniverse.cs プロジェクト: domisterwoozy/LabBox
 public static Optional<IBody> RaySelect(this IUniverse uni, Vector3 origin, Vector3 dir, IRay rayCastProvider = null)
 {
     if (rayCastProvider == null) rayCastProvider = new Ray();
     double furthestBodyPos = uni.Bodies.Max(b => (b.Position() - origin).Magnitude) + 100; // need to tune this. need to basically find the max dimension size of the biggest object
     var res = rayCastProvider.Cast(uni.Bodies.Select(b => new TransformedObj<IEdgeIntersector>(b.Dynamics.Transform, b.CollisionShape)), origin, dir, furthestBodyPos);
     return
         res.Match(
             hit => uni.Bodies.Single(b => b.CollisionShape == hit.HitObject.Obj).ToOptional(),
             () => Optional<IBody>.Nothing
         );
 }
コード例 #4
0
        public static IList<Point> GetIntersects(ICircle circle, IRay line)
        {
            IList<Point> list = new List<Point>();

            double a = Math.Pow(line.Vector.X, 2) + Math.Pow(line.Vector.Y, 2);
            double b = 2 * (line.Vector.X * (line.Point.X - circle.Center.X)
                + line.Vector.Y * (line.Point.Y - circle.Center.Y));

            double c = Math.Pow(circle.Center.X, 2) + Math.Pow(circle.Center.Y, 2);
            c += Math.Pow(line.Point.X, 2) + Math.Pow(line.Point.Y, 2);
            c -= 2 * (circle.Center.X * line.Point.X + circle.Center.Y * line.Point.Y);
            c -= Math.Pow(circle.Radius, 2);
            double bb4ac = b * b - 4 * a * c;

            if (bb4ac < 0)
                return list;
            else if (bb4ac == 0)
            {
                double mu = -b / (2 * a);
                Point intersectionPoint = new Point(line.Point.X + mu * line.Vector.X,
                                                    line.Point.Y + mu * line.Vector.Y);
                list.Add(intersectionPoint);
            }
            else
            {

                double mu = -b + Math.Sqrt(bb4ac) / (2 * a);
                Point intersectionPoint1 = new Point(line.Point.X + mu * line.Vector.X,
                                                    line.Point.Y + mu * line.Vector.Y);
                mu = -b - Math.Sqrt(bb4ac) / (2 * a);
                Point intersectionPoint2 = new Point(line.Point.X + mu * line.Vector.X,
                                                    line.Point.Y + mu * line.Vector.Y);

                list.Add(intersectionPoint1);
                list.Add(intersectionPoint2);
            }

            return list;
        }
コード例 #5
0
        /// <summary> Sample the <paramref name="scene"/> with a <paramref name="sample"/> returning a color found </summary>
        /// <param name="scene">The <see cref="IScene"/> to sample </param>
        /// <param name="ray">The <see cref="Ir4"/> to trace through the <paramref name="scene"/> </param>
        /// <param name="spectrum">The throughput <see cref="ISpectrum"/></param>
        /// <param name="recursionDepth">The depth of recursion</param>
        /// <returns>The color found for the <see cref="ISample"/></returns>
        public ISpectrum Sample(IScene scene, IRay ray, ISpectrum spectrum, int recursionDepth)
        {
            if (spectrum.Equals(ISpectrum.Black))
            {
                return(ISpectrum.Black);
            }

            /// Russian Roulette
            float throughput = 1f;

            if (recursionDepth >= GauranteedRecursionDepth)
            {
                if (Utils.ThreadRandom.NextSingle() < RussianRouletteChance)
                {
                    return(ISpectrum.Black);
                }
                else
                {
                    throughput = 1f / RussianRouletteChance;
                }
            }

            /// Sample Distance
            IDistanceQuery?distanceQuery = scene.Trace(ray, spectrum);

            if (distanceQuery is null)
            {
                return(ISpectrum.Black);
            }
            Position1 distance = distanceQuery.DistanceDistribution.Sample(Utils.ThreadRandom);

            if (distance == Position1.PositiveInfinity)
            {
                return(ISpectrum.Black);
            }

            /// Sample Primitive
            IProbabilityDistribution <IPrimitive>?primitives = distanceQuery.TryGetPrimitives(distance);

            if (primitives is null)
            {
                throw new InvalidOperationException("Distance was sampled but no primitive was found");
            }
            IPrimitive primitive = primitives.Sample(Utils.ThreadRandom);

            /// Get Intersection Position
            Position3 position = primitive.Material.DensityProfile.GetPosition(ray, distance, primitive.Shape);

            /// Sample Material Orientation
            IProbabilityDistribution <Normal3>?orientations = primitive.Material.OrientationProfile.GetOrientations(position, ray.Direction, primitive.Shape);

            if (orientations is null)
            {
                return(ISpectrum.Black);
            }
            Normal3 orientation = orientations.Sample(Utils.ThreadRandom);

            /// Get Direct Illumination
            ISpectrum directIllumination = RGBColors.Black;

            if (primitive.Material.EmittanceProfile.IsEmitting)
            {
                directIllumination = primitive.Material.EmittanceProfile.GetEmittance(position, orientation, -ray.Direction);
            }

            /// Get Indirect Illumination
            ISpectrum indirectIllumination = RGBColors.Black;

            if (!primitive.Material.AbsorptionProfile.IsBlackBody)
            {
                /// Sample Direction
                IProbabilityDistribution <Normal3> directions = primitive.Material.ReflectionProfile.GetDirections(ray.Direction, position, orientation, spectrum);
                Normal3 direction = directions.Sample(Utils.ThreadRandom);

                /// Get Albedo
                ISpectrum albedo = primitive.Material.AbsorptionProfile.GetAlbedo(position, orientation, -direction);

                /// Get Ray
                IRay raySample = primitive.Material.DensityProfile.GetRay(position, orientation, direction);

                /// Sample Indirect Illumination
                indirectIllumination = albedo * Sample(scene, raySample, spectrum * albedo, recursionDepth + 1);
            }

            /// Light Throughput Calculation
            return((directIllumination + indirectIllumination) * throughput);
        }
コード例 #6
0
 public void Sample(float x, float y, float u0, float u1, float u2, out IRay ray, out float pdf)
 {
     throw new NotImplementedException();
 }
コード例 #7
0
ファイル: NodeManipulator.cs プロジェクト: venusdharan/Dynamo
        /// <summary>
        /// Highlights/Unhighlights Gizmo drawables on mouse roll-over
        /// </summary>
        /// <param name="clickRay"></param>
        private void HighlightGizmoOnRollOver(IRay clickRay)
        {
            var gizmos = GetGizmos(false);
            foreach (var item in gizmos)
            {
                item.UnhighlightGizmo(BackgroundPreviewViewModel);

                object hitObject;
                if (item.HitTest(clickRay.GetOriginPoint(), clickRay.GetDirectionVector(), out hitObject))
                {
                    item.HighlightGizmo(BackgroundPreviewViewModel, RenderPackageFactory);
                }
            }
        }
コード例 #8
0
ファイル: SimpleCamera.cs プロジェクト: HungryBear/rayden
        public void GetRay(double xp, double yp, out IRay cameraRay)
        {
            var u = (float)(2.0f * xp / w - 1.0f);
            var v = (float)(1.0f - 2.0f * yp / h);

            Vector rdir = mRight * u + mUp * v + this.Look;
            var rorig = (Position + rdir * 0.1f);
            rdir.Normalize();
            cameraRay = new RayData(rorig, rdir);
        }
コード例 #9
0
 public static Point? GetNearest(IRay i, Point p)
 {
     var ps = GetIntersections(i, new Ray2D(p, p + i.Vector.GetNormal()));
     return ps.Count == 1 ? new Point?(ps[0]) : null;
 }
コード例 #10
0
 public Position3 GetPosition(IRay ray, Position1 distance, IShape shape)
 {
     return(shape.IntersectPosition(ray, distance));
 }
コード例 #11
0
 public IDistanceDistribution?GetDistances(IRay ray, ISpectrum spectrum, IInterval interval)
 {
     return(ray.WithinBounds(interval.Entry) ? new DeltaDistance(interval.Entry) : null);
 }
コード例 #12
0
ファイル: RayExtensions.cs プロジェクト: esandre/Lib
 /// <summary>
 /// Returns an Enumerable enumerating the ray
 /// </summary>
 public static IEnumerable <TPayload> ToEnumerable <TPayload>(this IRay <TPayload> ray) => new RayEnumerableAdapter <TPayload>(ray);
コード例 #13
0
ファイル: PinholeCamera.cs プロジェクト: HungryBear/rayden
 public void Sample(float x, float y, float u0, float u1, float u2, out IRay ray, out float pdf)
 {
     pdf = 1f;
     GetRay(x,y, out ray);
 }
コード例 #14
0
ファイル: BaseCamera.cs プロジェクト: HungryBear/rayden
 public void GetRay(double x, double y, out IRay cameraRay)
 {
     RayData r;
     this.GetRay(x, y, out r);
     cameraRay = r;
 }
コード例 #15
0
 /// <summary> Handle input for the <see cref="InteractiveObserver"/> </summary>
 /// <param name="keyboard">The <see cref="KeyboardState"/> to handle input from</param>
 /// <param name="mouse">The <see cref="MouseState"/> to handle input from</param>
 public void HandleInput(KeyboardState keyboard, MouseState mouse)
 {
     if (keyboard.IsKeyPressed(Keys.F1))
     {
         Drawing = Drawing.Next();
     }
     if (keyboard.IsKeyPressed(Keys.F2))
     {
         Debug = Debug.Next();
     }
     if (keyboard.IsKeyPressed(Keys.F3))
     {
         TextColor = 0xffffff - TextColor;
     }
     if (keyboard.IsKeyPressed(Keys.L))
     {
         CameraLock = !CameraLock;
     }
     if (!CameraLock)
     {
         if (mouse.WasButtonDown(MouseButton.Left) && !mouse.IsButtonDown(MouseButton.Left))
         {
             Vector2 position = new((float)mouse.X / Screen.Width, (float)mouse.Y / Screen.Height);
             IRay    ray      = Camera.GetCameraRay(position, position);
             Camera.SetViewDirection(ray.Direction);
         }
         if (keyboard.IsKeyDown(Keys.Space))
         {
             Camera.Move(Camera.Up * MoveSpeed);
         }
         if (keyboard.IsKeyDown(Keys.LeftShift))
         {
             Camera.Move(Camera.Down * MoveSpeed);
         }
         if (keyboard.IsKeyDown(Keys.W))
         {
             Camera.Move(Camera.Front * MoveSpeed);
         }
         if (keyboard.IsKeyDown(Keys.A))
         {
             Camera.Move(Camera.Left * MoveSpeed);
         }
         if (keyboard.IsKeyDown(Keys.S))
         {
             Camera.Move(Camera.Back * MoveSpeed);
         }
         if (keyboard.IsKeyDown(Keys.D))
         {
             Camera.Move(Camera.Right * MoveSpeed);
         }
         if (keyboard.IsKeyPressed(Keys.Equal))
         {
             Camera.HorizontalFOV *= 1f + FOVSensitivity;
         }
         if (keyboard.IsKeyPressed(Keys.Minus))
         {
             Camera.HorizontalFOV /= 1f + FOVSensitivity;
         }
         if (keyboard.IsKeyDown(Keys.Up))
         {
             Camera.Rotate(Normal3.DefaultRight, -RotateSensitivity);
         }
         if (keyboard.IsKeyDown(Keys.Down))
         {
             Camera.Rotate(Normal3.DefaultRight, RotateSensitivity);
         }
         if (keyboard.IsKeyDown(Keys.Right))
         {
             Camera.Rotate(Normal3.DefaultUp, RotateSensitivity);
         }
         if (keyboard.IsKeyDown(Keys.Left))
         {
             Camera.Rotate(Normal3.DefaultUp, -RotateSensitivity);
         }
         if (keyboard.IsKeyDown(Keys.Q))
         {
             Camera.Rotate(Normal3.DefaultFront, RotateSensitivity);
         }
         if (keyboard.IsKeyDown(Keys.E))
         {
             Camera.Rotate(Normal3.DefaultFront, -RotateSensitivity);
         }
     }
 }
コード例 #16
0
        public static IList<Point> GetIntersects(ISegment line1, IRay line2)
        {
            IList<Point> list = new List<Point>();

            Ray2D Ray = new Ray2D(line1.StartPoint, line1.EndPoint);

            IList<Point> intersect = line2.Intersection(Ray);
            if (intersect.Count > 0 && (
                                       intersect[0].X > Math.Min(line1.StartPoint.X, line1.EndPoint.X)
                                    && intersect[0].X < Math.Max(line1.StartPoint.X, line1.EndPoint.X)
                                    && intersect[0].Y > Math.Min(line1.StartPoint.Y, line1.EndPoint.Y)
                                    && intersect[0].Y < Math.Max(line1.StartPoint.Y, line1.EndPoint.Y)
                                 )
                )
            {
                list.Add(intersect[0]);
            }

            return list;
        }
コード例 #17
0
        public static IList<Point> GetIntersects(IRay line, IPoint point)
        {
            IList<Point> list = new List<Point>();

            double c = -(line.Vector.X * line.Point.X) - (line.Vector.Y * line.Point.Y);

            if ((line.Vector.X * point.X + line.Vector.Y * point.Y + c).IsEqual(0))
            {
                list.Add(new Point(point.X, point.Y));
            }

            return list;
        }
コード例 #18
0
 public IEnumerable <Position1> IntersectDistances(IRay ray)
 {
     return((BoundingBox as IIntersectable).Intersects(ray) ? OriginalShape.IntersectDistances(ray) : Enumerable.Empty <Position1>());
 }
コード例 #19
0
ファイル: RayEnumerableAdapter.cs プロジェクト: esandre/Lib
 /// <summary>
 /// Constructor
 /// </summary>
 public RayEnumerableAdapter(IRay <TPayload> ray) : base(ray.Origin)
 {
 }
コード例 #20
0
 public static Point GetOriginPoint(this IRay ray)
 {
     return(ray.Origin.ToPoint());
 }
コード例 #21
0
 public void GetRay(double x, double y, out IRay cameraRay) {
     throw new NotImplementedException();
 }
コード例 #22
0
 public static Vector GetDirectionVector(this IRay ray)
 {
     return(ray.Direction.ToVector());
 }
コード例 #23
0
        /// <summary>
        /// Highlights/Unhighlights Gizmo drawables on mouse roll-over
        /// </summary>
        /// <param name="clickRay"></param>
        private void HighlightGizmoOnRollOver(IRay clickRay)
        {
            var gizmos = GetGizmos(false);
            foreach (var item in gizmos)
            {
                item.UnhighlightGizmo();

                using (var originPt = clickRay.GetOriginPoint())
                using (var dirVec = clickRay.GetDirectionVector())
                {
                    object hitObject;
                    if (item.HitTest(originPt, dirVec, out hitObject))
                    {
                        item.HighlightGizmo();
                        return;
                    }
                }
            }
        }
コード例 #24
0
ファイル: TrendLineAlert.cs プロジェクト: fandres70/custom
        /// <summary>
        /// Called on each bar update event (incoming tick)
        /// </summary>
        protected override void OnBarUpdate()
        {
            //If we are not processing the current bar, return
            if (CurrentBar != Bars.GetBar(DateTime.Now))
            {
                return;
            }

            //Get current bid
            double bid = Bars.GetClose(Bars.GetBar(DateTime.Now));

            if (previous_bid < 0)
            {
                previous_bid = bid;
            }


            IDrawObject drawing_object = DrawObjects[trendLineTag];

            //Reset if drawing object is deleted or does not exist...
            if (drawing_object == null)
            {
                Type = null; AlertDone = false;
            }

            if (drawing_object != null && (drawing_object.DrawType == DrawType.Ray ||
                                           drawing_object.DrawType == DrawType.ExtendedLine ||
                                           drawing_object.DrawType == DrawType.Line))
            {
                double   y1, y2;
                int      bar1, bar2;
                DateTime time1, time2;
                if (drawing_object.DrawType == DrawType.Ray)
                {
                    IRay ray = (IRay)drawing_object;
                    y1    = ray.Anchor1Y;
                    y2    = ray.Anchor2Y;
                    time1 = ray.Anchor1Time;
                    time2 = ray.Anchor2Time;
                    bar1  = ray.Anchor1BarsAgo;
                    bar2  = ray.Anchor2BarsAgo;
                }
                else if (drawing_object.DrawType == DrawType.ExtendedLine)
                {
                    IExtendedLine line = (IExtendedLine)drawing_object;
                    y1    = line.StartY;
                    y2    = line.EndY;
                    time1 = line.StartTime;
                    time2 = line.EndTime;
                    bar1  = line.StartBarsAgo;
                    bar2  = line.EndBarsAgo;
                }
                else
                {
                    ILine line = (ILine)drawing_object;
                    y1    = line.StartY;
                    y2    = line.EndY;
                    time1 = line.StartTime;
                    time2 = line.EndTime;
                    bar1  = line.StartBarsAgo;
                    bar2  = line.EndBarsAgo;
                }


                //Reset alert if object has moved
                if ((time1 != this.sTime1 || time2 != this.sTime2 || y1 != this.sY1 || y2 != this.sY2) && this.sTime1 != null && this.sTime2 != null)
                {
                    Type = null; AlertDone = false;
                }

                if (AlertDone == false)
                {
                    //Store anchor to detect if object has moved
                    this.sTime1 = time1; this.sTime2 = time2; this.sY1 = y1; this.sY2 = y2;

                    //Calculate price target
                    double y     = y2 - y1;
                    double x     = bar1 - bar2;
                    double slope = y / x;

                    double deltaY       = bar2 * slope;               //time difference in ticks * slope
                    double price_target = Math.Round(y2 + deltaY, 5);

                    //IF price is below current price target or straddles it, THEN we alert when the bid>=price_target
                    if (Type == null && (price_target - previous_bid) >= 0)
                    {
                        Type = "up";
                    }
                    if (Type == null && (previous_bid - price_target) >= 0)
                    {
                        Type = "down";
                    }

                    previous_bid = bid;

                    if (Type == "up" && bid >= price_target)
                    {
                        Alert("TrendLineAlert", NinjaTrader.Cbi.Priority.High, "Reached Trend Line @ " + price_target, AlertSound, 10, Color.Black, Color.Yellow);
                        AlertDone = true;
                    }
                    if (Type == "down" && bid <= price_target)
                    {
                        Alert("TrendLineAlert", NinjaTrader.Cbi.Priority.High, "Reached Trend Line @ " + price_target, AlertSound, 10, Color.Black, Color.Yellow);
                        AlertDone = true;
                    }
                }
            }
        }
コード例 #25
0
        public void GetRay(double x, double y, out IRay cameraRay)
        {

            cameraRay = this.GetRay((float)x, (float)y);
        }
コード例 #26
0
ファイル: Uniform.cs プロジェクト: atharkes/raytracer
 public Position3 GetPosition(IRay ray, Position1 distance, IShape shape)
 {
     return(ray.Travel(distance));
 }
コード例 #27
0
        public void Sample(float xp, float yp, float u0, float u1, float u2, out IRay r, out float pdf)
        {
            Point Pras = new Point(xp, yp, 0);
            //Point Pcamera = UnProject(ref Pras);
            var u = 2.0f * xp / Width - 1.0f;
            var v = 1.0f - 2.0f * yp / Height;

            Vector ray_dir = new Vector(x.x * u + y.x * v + dir.x, x.y * u + y.y * v + dir.y, x.z * u + y.z * v + dir.z);
            Vector ray_target = (Vector)(Position + ray_dir * focal_scale);

            Point ray_origin = Position;

            var ray = new RayData(ray_origin, ray_dir, 0f, 1e20f);
            // Modify ray for depth of field
            if (lensRadius > 0f)
            {
                // Sample point on lens
                float lensU = 0f, lensV = 0f;
                float samplelensU = rnd.NextFloat();
                float samplelensV = rnd.NextFloat();

                MC.ConcentricSampleDisk(samplelensU, samplelensV, ref lensU, ref lensV);
                lensU *= lensRadius;
                lensV *= lensRadius;

                ray_target += lensRadius * (lensU * Vector.Normalize(x) + lensV * Vector.Normalize(y));


                // Compute point on plane of focus
                //float ft = focalDistance / ray.Dir.z;
                //Point Pfocus = ray.Point(ft);

                // Update ray for effect of lens
                ray.Org = ray_origin;
                ray.Dir = Vector.Normalize(ray_target - (Vector)ray_origin);
            }
            pdf = 1;
            r = (IRay)ray;

        }
コード例 #28
0
        protected override void OnBarUpdate()
        {
            //DETERMINE LOCATION OF LAST UP/DOWN TREND LINES
            signal = 0;
            int upTrendOccurence = 1;    int upTrendStartBarsAgo = 0;    int upTrendEndBarsAgo = 0;
            int downTrendOccurence = 1;    int downTrendStartBarsAgo = 0;    int downTrendEndBarsAgo = 0;

            // Only calculate new autotrend line if ray hasent been put into manual mode by unlocking current ray
            if (((DrawObjects["UpTrendRay"] == null) || (DrawObjects["UpTrendRay"].Locked)) && ((DrawObjects["DownTrendRay"] == null) || (DrawObjects["DownTrendRay"].Locked)))
//		if (  (DrawObjects["UpTrendRay"].Locked) || (DrawObjects["DowntrendTrendRay"].Locked) )
            {    //Only do the following if existing ray is in auto mode
                 // Calculate up trend line
                upTrendOccurence = 1;
                while (Low[upTrendEndBarsAgo] <= Low[upTrendStartBarsAgo])
                {
                    upTrendStartBarsAgo = Swing(strength).SwingLowBar(0, upTrendOccurence + 1, CurrentBar);
                    upTrendEndBarsAgo   = Swing(strength).SwingLowBar(0, upTrendOccurence, CurrentBar);
                    if (upTrendStartBarsAgo < 0 || upTrendEndBarsAgo < 0)
                    {
                        break;
                    }
                    upTrendOccurence++;
                }
                // Calculate down trend line
                downTrendOccurence = 1;
                while (High[downTrendEndBarsAgo] >= High[downTrendStartBarsAgo])
                {
                    downTrendStartBarsAgo = Swing(strength).SwingHighBar(0, downTrendOccurence + 1, CurrentBar);
                    downTrendEndBarsAgo   = Swing(strength).SwingHighBar(0, downTrendOccurence, CurrentBar);
                    if (downTrendStartBarsAgo < 0 || downTrendEndBarsAgo < 0)
                    {
                        break;
                    }
                    downTrendOccurence++;
                }
            }
            // Clear out arrows that mark trend line breaks unless ShowHistory flag is true
            if (!showHistory)
            {
                RemoveDrawObject("DownTrendBreak");
            }
            if (!showHistory)
            {
                RemoveDrawObject("UpTrendBreak");
            }

            //PROCESS UPTREND LINE IF CURRENT
            if (upTrendStartBarsAgo > 0 && upTrendEndBarsAgo > 0 && upTrendStartBarsAgo < downTrendStartBarsAgo)
            {
                RemoveDrawObject("DownTrendRay");
                double startBarPrice = Low[upTrendStartBarsAgo];
                double endBarPrice   = Low[upTrendEndBarsAgo];
                double changePerBar  = (endBarPrice - startBarPrice) / (Math.Abs(upTrendEndBarsAgo - upTrendStartBarsAgo));
                //Test to see if this is a new trendline and increment lineCounter if so.
                if (startBarPrice != startBarPriceOld)
                {
                    direction = 1;                    //Signal that we have a new uptrend and put dot on trendline where new trend detected
                    if (showHistory)
                    {
                        DrawDot(CurrentBar.ToString(), true, 0, startBarPrice + (upTrendStartBarsAgo * changePerBar), UpTrendColor);
                    }
                    lineCount       = lineCount + 1;
                    triggerBarIndex = 0;
                    ResetAlert("Alert");
                }
                startBarPriceOld = startBarPrice;
                //
                // Draw the up trend line
                // If user has unlocked the ray use manual rays position instead of auto generated positions to track ray position
                if ((DrawObjects["UpTrendRay"] != null) && (!DrawObjects["UpTrendRay"].Locked))
                {
                    IRay upTrendRay = (IRay)DrawObjects["UpTrendRay"];
                    startBarPrice            = upTrendRay.Anchor1Y;
                    endBarPrice              = upTrendRay.Anchor2Y;
                    upTrendStartBarsAgo      = upTrendRay.Anchor1BarsAgo;
                    upTrendEndBarsAgo        = upTrendRay.Anchor2BarsAgo;
                    changePerBar             = (endBarPrice - startBarPrice) / (Math.Abs(upTrendRay.Anchor2BarsAgo - upTrendRay.Anchor1BarsAgo));
                    upTrendRay.Pen.DashStyle = DashStyle.Dash;
                    upTrendRay.Pen.Color     = Color.Blue;
                }
                else
                {
                    DrawRay("UpTrendRay", false, upTrendStartBarsAgo, startBarPrice, upTrendEndBarsAgo, endBarPrice, UpTrendColor, DashStyle.Solid, lineWidth);
                }
                //Draw the history line that will stay persistent on chart using lineCounter to establish a unique name
                if (showHistory)
                {
                    DrawLine("HistoryLine" + lineCount.ToString(), false, upTrendStartBarsAgo, startBarPrice, 0, startBarPrice + (upTrendStartBarsAgo * changePerBar), UpHistColor, DashStyle.Solid, lineWidth);
                }
                //SET RETURN VALUES FOR INDICATOR
                // Check for an uptrend line break
                trendPrice = (startBarPrice + (upTrendStartBarsAgo * changePerBar));
                for (int barsAgo = upTrendEndBarsAgo - 1; barsAgo >= 0; barsAgo--)
                {
                    if (Close[barsAgo] < endBarPrice + (Math.Abs(upTrendEndBarsAgo - barsAgo) * changePerBar))
                    {
                        if (showHistory)
                        {
                            DrawArrowDown("UpTrendBreak" + lineCount.ToString(), barsAgo, High[barsAgo] + TickSize, downTrendColor);
                        }
                        else
                        {
                            DrawArrowDown("UpTrendBreak", barsAgo, High[barsAgo] + TickSize, downTrendColor);
                        }
                        // Set the break signal only if the break is on the right most bar
                        if (barsAgo == 0)
                        {
                            signal = -1;
                        }
                        // Alert will only trigger in real-time
                        if (AlertOnBreak && triggerBarIndex == 0)
                        {
                            triggerBarIndex = CurrentBar - upTrendEndBarsAgo;
                            Alert("Alert", Priority.High, "Up trend line broken", "Alert2.wav", 100000, Color.Black, Color.Red);
                        }
                        break;
                    }
                }
            }


            else
            //DETECT AND PROCESS DOWNTREND LINE	IF CURRENT
            if (downTrendStartBarsAgo > 0 && downTrendEndBarsAgo > 0 && upTrendStartBarsAgo > downTrendStartBarsAgo)
            {
                RemoveDrawObject("UpTrendRay");
                double startBarPrice = High[downTrendStartBarsAgo];
                double endBarPrice   = High[downTrendEndBarsAgo];
                double changePerBar  = (endBarPrice - startBarPrice) / (Math.Abs(downTrendEndBarsAgo - downTrendStartBarsAgo));
                //Test to see if this is a new trendline and increment lineCount if so.
                if (startBarPrice != startBarPriceOld)
                {
                    direction = -1;                             //signl that we have a new downtrend
                    if (showHistory)
                    {
                        DrawDot(CurrentBar.ToString(), true, 0, startBarPrice + (downTrendStartBarsAgo * changePerBar), DownTrendColor);
                    }
                    lineCount       = lineCount + 1;
                    triggerBarIndex = 0;
                    ResetAlert("Alert");
                }
                startBarPriceOld = startBarPrice;
                //
                // Draw the down trend line
                // If user has unlocked the ray use manual rays position instead
                if ((DrawObjects["DownTrendRay"] != null) && (!DrawObjects["DownTrendRay"].Locked))
                {
                    IRay downTrendRay = (IRay)DrawObjects["DownTrendRay"];
                    startBarPrice              = downTrendRay.Anchor1Y;
                    endBarPrice                = downTrendRay.Anchor2Y;;
                    downTrendStartBarsAgo      = downTrendRay.Anchor1BarsAgo;
                    downTrendEndBarsAgo        = downTrendRay.Anchor2BarsAgo;
                    changePerBar               = (endBarPrice - startBarPrice) / (Math.Abs(downTrendRay.Anchor2BarsAgo - downTrendRay.Anchor1BarsAgo));
                    downTrendRay.Pen.DashStyle = DashStyle.Dash;
                    downTrendRay.Pen.Color     = Color.Blue;
                }
                else
                {
                    DrawRay("DownTrendRay", false, downTrendStartBarsAgo, startBarPrice, downTrendEndBarsAgo, endBarPrice, DownTrendColor, DashStyle.Solid, lineWidth);
                }
                if (showHistory)
                {
                    DrawLine("HistoryLine" + lineCount.ToString(), false, downTrendStartBarsAgo, startBarPrice, 0, startBarPrice + (downTrendStartBarsAgo * changePerBar), downHistColor, DashStyle.Solid, lineWidth);
                }
                //SET RETURN VALUES FOR INDICATOR
                // Check for a down trend line break
                trendPrice = (startBarPrice + (downTrendStartBarsAgo * changePerBar));
                for (int barsAgo = downTrendEndBarsAgo - 1; barsAgo >= 0; barsAgo--)
                {                //	direction=-1;
                    if (Close[barsAgo] > endBarPrice + (Math.Abs(downTrendEndBarsAgo - barsAgo) * changePerBar))
                    {
                        if (showHistory)
                        {
                            DrawArrowUp("DownTrendBreak" + lineCount.ToString(), barsAgo, Low[barsAgo] - TickSize, upTrendColor);
                        }
                        else
                        {
                            DrawArrowUp("DownTrendBreak", barsAgo, Low[barsAgo] - TickSize, upTrendColor);
                        }
                        // Set the break signal only if the break is on the right most bar
                        if (barsAgo == 0)
                        {
                            signal = 1;
                        }
                        // Alert will only trigger in real-time
                        if (AlertOnBreak && triggerBarIndex == 0)
                        {
                            triggerBarIndex = CurrentBar - downTrendEndBarsAgo;
                            Alert("Alert", Priority.High, "Down trend line broken", "Alert2.wav", 100000, Color.Black, Color.Green);
                        }
                        break;
                    }
                }
            }
        }