/// <summary> /// Performs a pick operation on the diagram annotations</summary> /// <param name="p">Picking point</param> /// <returns>Information about which annotation, if any, was hit by point</returns> public AnnotationHitEventArgs Pick(Point p) { if (m_annotatedDiagram != null) { if (m_transformAdapter != null) { p = GdiUtil.InverseTransform(m_transformAdapter.Transform, p); } foreach (IAnnotation annotation in m_annotatedDiagram.Annotations) { Rectangle bounds = GetBounds(annotation); int tolerance = m_theme.PickTolerance; bounds.Inflate(tolerance, tolerance); if (bounds.Contains(p)) { bounds.Inflate(tolerance * -2, tolerance * -2); DiagramLabel label = null; if (bounds.Contains(p)) { label = new DiagramLabel(bounds, TextFormatFlags.Default); } return(new AnnotationHitEventArgs(annotation, label)); } } } return(new AnnotationHitEventArgs()); }
/// <summary> /// Begins a label editing operation</summary> /// <param name="namingContext">Naming context that performs naming operations</param> /// <param name="item">Item with label</param> /// <param name="label">Information about label</param> public void BeginEdit(INamingContext namingContext, object item, DiagramLabel label) { m_namingContext = namingContext; m_item = item; m_label = label; m_labelBounds = label.Bounds; float fontScale = 1.0f; if (m_transformAdapter != null) { Matrix transform = m_transformAdapter.Transform; m_labelBounds = GdiUtil.Transform(transform, m_labelBounds); // in case of non-uniform scaling, prefer vertical (y) scale for magnification factor; // Timeline control is the only example of non-uniform scale right now, and y-scale works // better in this case. fontScale *= transform.Elements[3]; } m_textBox.Text = m_namingContext.GetName(m_item); Font font = this.AdaptedControl.Font; m_textBox.Font = new Font(font.FontFamily, (int)(font.SizeInPoints * fontScale)); TextFormatFlags flags = m_label.Format; m_textBox.Multiline = (flags & TextFormatFlags.SingleLine) == 0; HorizontalAlignment alignment = HorizontalAlignment.Left; if ((flags & TextFormatFlags.Right) != 0) { alignment = HorizontalAlignment.Right; } else if ((flags & TextFormatFlags.HorizontalCenter) != 0) { alignment = HorizontalAlignment.Center; } m_textBox.TextAlign = alignment; SizeTextBox(); m_textBox.Visible = true; m_textBox.Focus(); m_textBox.SelectAll(); }
private void selectionAdapter_SelectedItemHit(object sender, DiagramHitEventArgs e) { m_itemHitRecord = e.HitRecord; // hit on diagram label part? DiagramLabel hitLabel = e.HitRecord.Part.As <DiagramLabel>(); if (hitLabel != null) { INamingContext namingContext = AdaptedControl.ContextAs <INamingContext>(); if (namingContext != null) { // if label editing is enabled, mouse is over label, and item can be named, open it for edit if (namingContext.CanSetName(e.HitRecord.Item)) { m_hitLabel = hitLabel; m_labelEditTimer.Interval = SystemInformation.DoubleClickTime; m_labelEditTimer.Enabled = true; } } } }
/// <summary> /// Begins a label editing operation</summary> /// <param name="namingContext">Naming context that performs naming operations</param> /// <param name="item">Item with label</param> /// <param name="label">Information about label</param> public void BeginEdit(INamingContext namingContext, object item, DiagramLabel label) { m_namingContext = namingContext; m_item = item; m_label = label; m_labelBounds = label.Bounds; float fontScale = 1.0f; if (m_transformAdapter != null) { Matrix transform = m_transformAdapter.Transform; m_labelBounds = GdiUtil.Transform(transform, m_labelBounds); // in case of non-uniform scaling, prefer vertical (y) scale for magnification factor; // Timeline control is the only example of non-uniform scale right now, and y-scale works // better in this case. fontScale *= transform.Elements[3]; } m_textBox.Text = m_namingContext.GetName(m_item); Font font = this.AdaptedControl.Font; m_textBox.Font = new Font(font.FontFamily, (int)(font.SizeInPoints * fontScale)); TextFormatFlags flags = m_label.Format; m_textBox.Multiline = (flags & TextFormatFlags.SingleLine) == 0; HorizontalAlignment alignment = HorizontalAlignment.Left; if ((flags & TextFormatFlags.Right) != 0) alignment = HorizontalAlignment.Right; else if ((flags & TextFormatFlags.HorizontalCenter) != 0) alignment = HorizontalAlignment.Center; m_textBox.TextAlign = alignment; SizeTextBox(); m_textBox.Visible = true; m_textBox.Focus(); m_textBox.SelectAll(); }
/// <summary> /// Constructor, annotation hit</summary> /// <param name="annotation">Annotation item</param> /// <param name="label">Editable text part, or null if hit on edge</param> public AnnotationHitEventArgs(IAnnotation annotation, DiagramLabel label) { Item = annotation; Part = label; }
/// <summary> /// Performs a pick operation on the diagram annotations</summary> /// <param name="p">Picking point</param> /// <returns>Information about which annotation, if any, was hit by point</returns> public AnnotationHitEventArgs Pick(Point p) { if (m_annotatedDiagram != null) { if (m_transformAdapter != null) p = GdiUtil.InverseTransform(m_transformAdapter.Transform, p); foreach (IAnnotation annotation in m_annotatedDiagram.Annotations) { Rectangle bounds = GetBounds(annotation); int tolerance = m_theme.PickTolerance; bounds.Inflate(tolerance, tolerance); if (bounds.Contains(p)) { bounds.Inflate(tolerance * -2, tolerance * -2); DiagramLabel label = null; if (bounds.Contains(p)) label = new DiagramLabel(bounds, TextFormatFlags.Default); return new AnnotationHitEventArgs(annotation, label); } } } return new AnnotationHitEventArgs(); }
/// <summary> /// Performs a pick operation on the diagram annotations</summary> /// <param name="p">Picking point</param> /// <returns>Information about which annotation, if any, was hit by point</returns> public AnnotationHitEventArgs Pick(Point p) { if (m_annotatedDiagram != null) { if (m_transformAdapter != null) p = GdiUtil.InverseTransform(m_transformAdapter.Transform, p); foreach (IAnnotation annotation in m_annotatedDiagram.Annotations.Reverse()) { Rectangle bounds = GetBounds(annotation); if (bounds.IsEmpty) continue; var inflated = bounds; int tolerance = m_theme.PickTolerance; inflated.Inflate(tolerance, tolerance); if (inflated.Contains(p) && m_annotationEditors.ContainsKey(annotation)) { // check titlebar var titlebarRect = new RectangleF(bounds.Left + 2 * tolerance, bounds.Y - tolerance, bounds.Width - 4 * tolerance, Margin.Top + tolerance); if (titlebarRect.Contains(p)) { return new AnnotationHitEventArgs(annotation, new DiagramTitleBar(annotation)); } var annotationData = m_annotationEditors[annotation]; // check scroll bar if (annotationData.VerticalScrollBarVisibe) { var scrollbarRect = new RectangleF(bounds.Right - Margin.Right - ScrollBarWidth - 2 * ScrollBarMargin, bounds.Y, ScrollBarWidth + 2 * ScrollBarMargin, bounds.Height); if (scrollbarRect.Contains(p)) return new AnnotationHitEventArgs(annotation, new DiagramScrollBar(annotation, Orientation.Vertical)); } // check borders // check corners first var border = new RectangleF(bounds.Right - 2 * tolerance, bounds.Bottom - 2 * tolerance, 4 * tolerance, 4 * tolerance); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.LowerRightCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } border = new RectangleF(bounds.Left - 2 * tolerance, bounds.Top - 2 * m_theme.PickTolerance, 4 * tolerance, 4 * tolerance); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.UpperLeftCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } border = new RectangleF(bounds.Right - 2 * m_theme.PickTolerance, bounds.Top - 2 * m_theme.PickTolerance, 4 * tolerance, 4 * tolerance); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.UpperRightCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } border = new RectangleF(bounds.Left - 2 * m_theme.PickTolerance, bounds.Bottom - 2 * m_theme.PickTolerance, 4 * tolerance, 4 * tolerance); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.LowerLeftCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } border = new RectangleF(bounds.Left - m_theme.PickTolerance, bounds.Y, 2 * m_theme.PickTolerance, bounds.Height); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Left }; return new AnnotationHitEventArgs(annotation, borderPart); } border.Offset(bounds.Width, 0); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Right }; return new AnnotationHitEventArgs(annotation, borderPart); } border = new RectangleF(bounds.Left, bounds.Y - m_theme.PickTolerance, bounds.Width, 2 * m_theme.PickTolerance); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Top }; return new AnnotationHitEventArgs(annotation, borderPart); } border.Offset(0, bounds.Height); if (border.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Bottom }; return new AnnotationHitEventArgs(annotation, borderPart); } // check label inflated.Inflate(tolerance, tolerance); DiagramLabel label = null; if (inflated.Contains(p)) { var textBounds = new Rectangle(bounds.X + Margin.Left, bounds.Y + Margin.Top, (int)annotationData.TextLayout.LayoutWidth + SystemInformation.VerticalScrollBarWidth, (int)annotationData.TextLayout.LayoutHeight); label = new DiagramLabel(textBounds, TextFormatFlags.LeftAndRightPadding); // set initial editing position var contentBounds = new RectangleF(bounds.X + Margin.Left, bounds.Y + Margin.Top, bounds.Width - Margin.Size.Width, bounds.Height - Margin.Size.Height); contentBounds.Width = Math.Max(contentBounds.Width, MinimumWidth); contentBounds.Height = Math.Max(contentBounds.Height, MinimumHeight); PointF origin = new PointF(contentBounds.Location.X, contentBounds.Location.Y - annotationData.TopLine * m_theme.TextFormat.FontHeight); var result = new AnnotationHitEventArgs(annotation, label); result.Position = new PointF(p.X - origin.X, p.Y - origin.Y); return result; } } } } return new AnnotationHitEventArgs(); }
/// <summary> /// Performs hit test for a point, in client coordinates</summary> /// <param name="p">Pick point, in client coordinates</param> /// <returns>Hit record for a point, in client coordinates</returns> DiagramHitRecord IPickingAdapter2.Pick(Point p) { if (m_annotatedDiagram != null && !PickingDisabled) { if (m_transformAdapter != null) p = GdiUtil.InverseTransform(m_transformAdapter.Transform, p); foreach (IAnnotation annotation in m_annotatedDiagram.Annotations.Reverse()) { TextEditor textEditor; m_annotationEditors.TryGetValue(annotation, out textEditor); Rectangle bounds = GetBounds(annotation); if (bounds.IsEmpty && textEditor == null) continue; var inflated = bounds; int tolerance = m_theme.PickTolerance; inflated.Inflate(tolerance, tolerance); if (!inflated.Contains(p)) continue; Rectangle contentRect = bounds; contentRect.X += Margin.Left; contentRect.Y += Margin.Right; contentRect.Size -= Margin.Size; if (contentRect.Contains(p)) { // check scroll bar if (textEditor != null && textEditor.VerticalScrollBarVisibe) { var scrollbarRect = new Rectangle(bounds.Right - Margin.Right - ScrollBarWidth - 2 * ScrollBarMargin, bounds.Y, ScrollBarWidth + 2 * ScrollBarMargin, bounds.Height); if (scrollbarRect.Contains(p)) return new AnnotationHitEventArgs(annotation, new DiagramScrollBar(annotation, Orientation.Vertical)); } //var textBounds = new Rectangle(contentRect.X, contentRect.Y, // contentRect.Width, contentRect.Height); var textBounds = contentRect; DiagramLabel label = new DiagramLabel(textBounds, TextFormatFlags.LeftAndRightPadding); PointF origin = textEditor != null ? new PointF(contentRect.X, contentRect.Y - textEditor.GetLineYOffset(textEditor.TopLine)) : contentRect.Location; var result = new AnnotationHitEventArgs(annotation, label); result.Position = new PointF(p.X - origin.X, p.Y - origin.Y); return result; } //// check titlebar //var titlebarRect = new RectangleF(bounds.Left + 2 * tolerance, bounds.Y - tolerance, // bounds.Width - 4 * tolerance, Margin.Top + tolerance); //if (titlebarRect.Contains(p)) //{ // return new AnnotationHitEventArgs(annotation, new DiagramTitleBar(annotation)); //} // margin between inflated bounds and content bound. int leftPad = contentRect.X - inflated.X; int rightPad = inflated.Right - contentRect.Right; int topPad = contentRect.Y - inflated.Y; int bottomPad = inflated.Bottom - contentRect.Bottom; // lower right var corner = new Rectangle(contentRect.Right, contentRect.Bottom, rightPad, bottomPad); if (corner.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.LowerRightCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } // upper left corner = new Rectangle(inflated.X, inflated.Y, leftPad, topPad); if (corner.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.UpperLeftCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } // upper right corner = new Rectangle(contentRect.Right, inflated.Y, rightPad, topPad); if (corner.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.UpperRightCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } // lower left. corner = new Rectangle(inflated.X, contentRect.Bottom, leftPad, bottomPad); if (corner.Contains(p)) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.LowerLeftCorner }; return new AnnotationHitEventArgs(annotation, borderPart); } // right border. if (p.X >= contentRect.Right) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Right }; return new AnnotationHitEventArgs(annotation, borderPart); } // bottom border if (p.Y >= contentRect.Bottom) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Bottom }; return new AnnotationHitEventArgs(annotation, borderPart); } // left border if (p.X <= contentRect.X) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Left }; return new AnnotationHitEventArgs(annotation, borderPart); } // top border if (p.Y <= contentRect.Y) { var borderPart = new DiagramBorder(annotation) { Border = DiagramBorder.BorderType.Top }; return new AnnotationHitEventArgs(annotation, borderPart); } } } return new AnnotationHitEventArgs(); }