コード例 #1
0
ファイル: Conversion.cs プロジェクト: johnmensen/TradeSharp
        internal static PointF WorldToScreenF(PointD worldPt, RectangleD worldRect, RectangleD screenRect)
        {
            if ((Math.Abs(worldRect.Width) <= double.Epsilon) || (Math.Abs(worldRect.Height) <= double.Epsilon))
            {
                return worldPt.ToPointF();
            }
            if (double.IsNegativeInfinity(worldPt.Y)) worldPt.Y = worldRect.Bottom - 1;
            else if (double.IsInfinity(worldPt.Y)) worldPt.Y = worldRect.Top + 1;

            var td = new PointF
            {
                X = (float)((((worldPt.X - worldRect.Left) / worldRect.Width) * screenRect.Width) + screenRect.Left),
                Y = (float)
                    ((screenRect.Height -
                      (((worldPt.Y - worldRect.Top) / worldRect.Height) * screenRect.Height)) +
                     screenRect.Top)
            };
            const float maxDimx = 1048576f;
            if (td.X > maxDimx) td.X = maxDimx;
            if (td.X < -maxDimx) td.X = -maxDimx;
            if (td.Y > maxDimx) td.Y = maxDimx;
            if (td.Y < -maxDimx) td.Y = -maxDimx;
            return td;
        }
コード例 #2
0
        /// <summary>
        /// вернуть массив точек стрелочки в точку e
        /// </summary>        
        private PointF[] GetArrowPoints(PointD b, PointD e)
        {
            const double arrowA = Math.PI/8;
            const int arrowL = 8;

            //double spanAngle = Math.Atan2(e.Y - b.Y, e.X - b.X);
            var spanLen = Geometry.GetSpanLength(b, e);
            if (spanLen == 0) return new PointF[0];

            var c = e + (b - e)*(arrowL/spanLen);
            var c1 = Geometry.RotatePoint(c, e, -arrowA);
            var c2 = Geometry.RotatePoint(c, e, arrowA);
            return new[] { e.ToPointF(), c1.ToPointF(), c2.ToPointF() };
        }
コード例 #3
0
ファイル: TrendLine.cs プロジェクト: johnmensen/TradeSharp
 protected bool IsInObject(PointD a, PointD b,
     VectorGraphObject obj, Point ptClient, float tolerance)
 {
     var len = (float)Geometry.GetSpanLength(a, b);
     VectorGraphObject smb = obj.Copy();
     float scale = len / smb.Width;
     // масштабирование
     smb.Scale(scale, scale);
     // перенос
     smb.Move2Point(a.ToPointF());
     // наклон
     smb.Rotate((float)Math.Atan2(b.Y - a.Y, b.X - a.X));
     // проверить попадание
     return smb.IsPointIn(ptClient, tolerance);
 }
コード例 #4
0
        private void DrawTangent(List<PointD> screenPoints, Rectangle canvasRect, Graphics g, PenStorage penStorage,
                                 BrushesStorage brushStorage, Font font)
        {
            var ptLeft = points[0].X < points[1].X ? points[0] : points[1];
            var ptRight = points[0].X < points[1].X ? points[1] : points[0];
            var m1 = new PointD(cx + b * Math.Sin(angle), cy + b * Math.Cos(angle));
            var m2 = new PointD(cx + b * Math.Sin(angle + Math.PI), cy + b * Math.Cos(angle + Math.PI));
            var m = ptLeft.Y > ptRight.Y
                        ? m1.Y < m2.Y ? m1 : m2 // нижняя касательная для растущего эллипса
                        : m1.Y < m2.Y ? m2 : m1; // верхняя для падающего

            var o = new PointD(cx, cy);
            var r = new PointD(m.X - o.X, m.Y - o.Y);

            var pen = penStorage.GetPen(TangentColor);

            foreach (var level in tangentFiboLevels)
            {
                // нарисовать касательную или параллельную ей линию
                var A = new PointD(screenPoints[0].X + r.X * (level + 1), screenPoints[0].Y + r.Y * (level + 1));
                var B = new PointD(screenPoints[1].X + r.X * (level + 1), screenPoints[1].Y + r.Y * (level + 1));
                if (TangentType == EllipseTangentType.Прямая) StretchSpanToScreen(ref A, ref B, canvasRect);
                g.DrawLine(pen, A.ToPointF(), B.ToPointF());
                if (level == 0) continue;
                // нарисовать текстовую отметку
                var ptText = new PointD(o.X + r.X * (level + 1), o.Y + r.Y * (level + 1));
                var textSz = g.MeasureString(level.ToString(), font);
                var textRect = new Rectangle((int) (ptText.X - textSz.Width / 2 - 2),
                                             (int) (ptText.Y - textSz.Height / 2 - 2),
                                             (int) textSz.Width + 4, (int) textSz.Height + 4);
                var brushWhite = brushStorage.GetBrush(Color.FromArgb(60, pen.Color));
                g.FillRectangle(brushWhite, textRect);
                g.DrawRectangle(pen, textRect);
                var brushText = brushStorage.GetBrush(pen.Color);
                g.DrawString(level.ToString(), font, brushText, (float) ptText.X, (float) ptText.Y,
                             new StringFormat
                                 {
                                     Alignment = StringAlignment.Center,
                                     LineAlignment = StringAlignment.Center
                                 });
            }
        }
コード例 #5
0
        /// <summary>
        /// Получить описывающий 
        /// </summary>
        /// <param name="candles"></param>
        /// <param name="start"></param>
        /// <param name="end"></param>
        /// <returns></returns>
        private ChartEllipse BuildInclusiveEllipse(StockSeriesData candles, int start, int end)
        {
            if (start == end) return null;
            float startvalue, endvalue;
            if (candles[start].high > candles[end].high)
            {
                startvalue = candles[start].high;
                endvalue = candles[end].low;
            }
            else
            {
                startvalue = candles[start].low;
                endvalue = candles[end].high;
            }
            var A = new PointD(start, Convert.ToDouble(startvalue));
            var B = new PointD(end, Convert.ToDouble(endvalue));
            var C = new PointD();

            double angle;
            float cx, cy, a, b;
            var S = float.NaN;
            bool correctEllipse = false;
            // поиск охватывающего эллипса
            for (var i = start; i <= end; i++)
            {
                var d = new PointD(i, Convert.ToDouble(candles[i].high));
                correctEllipse = Geometry.GetEllipseParams(A.ToPointF(), B.ToPointF(), d.ToPointF(), out angle, out a, out b, out cx, out cy);
                if (float.IsNaN(S) || (correctEllipse && S < b))
                {
                    S = b;
                    C = d;
                }

                d = new PointD(i, Convert.ToDouble(candles[i].low));
                correctEllipse = Geometry.GetEllipseParams(A.ToPointF(), B.ToPointF(), d.ToPointF(), out angle, out a, out b, out cx, out cy);
                if (float.IsNaN(S) || (correctEllipse && S < b))
                {
                    S = b;
                    C = d;
                }
            }

            correctEllipse = // пересчитываем параметры эллипса
                Geometry.GetEllipseParams(A.ToPointF(), B.ToPointF(), C.ToPointF(), out angle, out a, out b, out cx, out cy);
            if (correctEllipse)
            {   // можно построить эллипс - рисуем его
                var newEllipse = new ChartEllipse { BuildTangent = true, angle = angle, a = a, b = b, cx = cx, cy = cy };

                newEllipse.AddPoint((float)A.X, (float)A.Y);
                newEllipse.AddPoint((float)B.X, (float)B.Y);
                newEllipse.AddPoint((float)C.X, (float)C.Y);

                var minIndex = newEllipse.points.Min(p => p.X);
                newEllipse.DateStart = owner.StockSeries.GetCandleOpenTimeByIndex((int)minIndex);
                return newEllipse;
            }
            return null;
        }