//-------------------------------------------------------------
//
// Copyright © Microsoft Corporation. All Rights Reserved.
//
//-------------------------------------------------------------
// @owner=alexgor, deliant
//=================================================================
// File: AnnotationDesign.cs
//
// Namespace: System.Web.UI.WebControls[Windows.Forms].Charting
//
// Classes: AnnotationCollectionEditor, AnchorPointUITypeEditor,
// AnchorPointNameTreeView, AnchorPointValueConverter,
// AnnotationAxisUITypeEditor, AnnotationAxisNameTreeView,
// AnnotationAxisValueConverter
//
// Purpose: Annotation design-time support classes.
//
// Reviewed:
//
//===================================================================
#region Used namespace
using System;
using System.Globalization;
using System.Collections;
using System.Collections.Specialized;
using System.ComponentModel;
using System.ComponentModel.Design;
using System.Data;
using System.Drawing;
using System.Drawing.Design;
using System.Drawing.Text;
using System.Drawing.Drawing2D;
using System.Windows.Forms;
using FastReport.Design;
using FastReport.DataVisualization.Charting;
using FastReport.DataVisualization.Charting.Data;
using FastReport.DataVisualization.Charting.ChartTypes;
using FastReport.DataVisualization.Charting.Utilities;
using FastReport.DataVisualization.Charting.Borders3D;
//using FastReport.DataVisualization.Charting.Design;
#if VS_DESIGN_TIME
using System.Web.UI.Design;
using System.Web.UI.WebControls.Charting.Design;
using System.Web.UI.WebControls.Charting.Data;
using System.Web.UI.WebControls.Charting.Utilities;
#endif
#endregion
#if WINFORMS_CONTROL
namespace System.Windows.Forms.Charting.Design
#else
namespace System.Web.UI.WebControls.Charting.Design
#endif
{
#if !SMART_CLIENT
#if VS_DESIGN_TIME
///
/// Designer editor for the Animation Collection collection.
///
[
SRDescription("DescriptionAttributeAnnotationCollectionEditor_AnnotationCollectionEditor")
]
public class AnnotationCollectionEditor : ChartCollectionEditor
{
#region Methods
///
/// Object constructor.
///
public AnnotationCollectionEditor() : base(typeof(AnnotationCollection))
{
}
///
/// Gets the data types that this collection editor can contain.
///
/// An array of data types that this collection can contain.
protected override Type[] CreateNewItemTypes()
{
return new Type[] {
typeof(LineAnnotation),
typeof(VerticalLineAnnotation),
typeof(HorizontalLineAnnotation),
typeof(TextAnnotation),
typeof(RectangleAnnotation),
typeof(EllipseAnnotation),
typeof(ArrowAnnotation),
typeof(Border3DAnnotation),
typeof(CalloutAnnotation),
typeof(PolylineAnnotation),
typeof(PolygonAnnotation),
typeof(ImageAnnotation),
typeof(AnnotationGroup)
};
}
///
/// Create annotation instance in the editor
///
/// Item type.
/// Newly created item.
protected override object CreateInstance(Type itemType)
{
Chart control = (Chart)GetChartReference(Context.Instance);
// Call base class
Annotation annotation = base.CreateInstance(itemType) as Annotation;
// Generate unique name
if(control != null)
{
control.Annotations.AssignUniqueName(annotation);
}
return annotation;
}
#endregion // Methods
}
///
/// UI type editor for the annotation anchor point
///
public class AnchorPointUITypeEditor : System.Drawing.Design.UITypeEditor
{
#region Editor methods and properties
///
/// Display a dropdown list with check boxes.
///
/// Editing context.
/// Provider.
/// Value to edit.
/// Result
public override object EditValue(ITypeDescriptorContext context, IServiceProvider provider, object value)
{
if (context != null && context.Instance != null && provider != null)
{
IWindowsFormsEditorService edSvc = (IWindowsFormsEditorService)provider.GetService(typeof(IWindowsFormsEditorService));
if (edSvc != null &&
context.Instance is Annotation)
{
// Create control for editing
AnchorPointNameTreeView control = new AnchorPointNameTreeView(
edSvc,
(Annotation)context.Instance,
value as DataPoint);
// Show drop down control
edSvc.DropDownControl(control);
// Get new enumeration value
value = control.GetNewValue();
// Dispose control
control.Dispose();
}
}
return value;
}
///
/// Gets editing style.
///
/// Editing context.
/// Editor style.
public override UITypeEditorEditStyle GetEditStyle(ITypeDescriptorContext context)
{
if (context != null && context.Instance != null)
{
return UITypeEditorEditStyle.DropDown;
}
return base.GetEditStyle(context);
}
#endregion
}
///
/// Anchor data points name tree view, which is used for the UI type editing.
///
internal class AnchorPointNameTreeView : System.Windows.Forms.TreeView
{
#region Control fields
// Annotation object to edit
private Annotation annotation = null;
private DataPoint dataPoint = null;
IWindowsFormsEditorService edSvc = null;
#endregion
#region Control constructor
///
/// Public constructor.
///
/// Editor service.
/// Annotation to edit.
/// Annotation anchor data point to edit.
public AnchorPointNameTreeView(
IWindowsFormsEditorService edSvc,
Annotation annotation,
DataPoint dataPoint)
{
// Set editable value
this.annotation = annotation;
this.dataPoint = dataPoint;
this.edSvc = edSvc;
// Set control border style
this.BorderStyle = System.Windows.Forms.BorderStyle.None;
// Fill tree with data point names
this.FillTree();
}
#endregion
#region Control methods
///
/// Fills data points name tree.
///
private void FillTree()
{
bool nodeSelected = false;
this.BeginUpdate();
// Add "None" option
System.Windows.Forms.TreeNode noPoint = this.Nodes.Add(Constants.NotSetValue);
// Get chart object
if(this.annotation != null &&
annotation.GetAnnotationGroup() == null &&
this.annotation.Chart != null)
{
Chart chart = this.annotation.Chart;
// Loop through all series
foreach(Series series in chart.Series)
{
System.Windows.Forms.TreeNode seriesNode = this.Nodes.Add(series.Name);
seriesNode.Tag = series;
// Indicate that there are no points in series
if(series.Points.Count == 0)
{
System.Windows.Forms.TreeNode noPointNode = seriesNode.Nodes.Add("(empty)");
}
// Loop through all points
int index = 1;
foreach(DataPoint point in series.Points)
{
System.Windows.Forms.TreeNode dataPointNode = seriesNode.Nodes.Add("DataPoint" + index.ToString(CultureInfo.InvariantCulture));
dataPointNode.Tag = point;
++index;
// Check if this node should be selected
if(point == dataPoint)
{
seriesNode.Expand();
this.SelectedNode = dataPointNode;
nodeSelected = true;
}
}
}
}
// Select default node
if(!nodeSelected)
{
this.SelectedNode = noPoint;
}
this.EndUpdate();
}
///
/// Gets new data point.
///
/// New enum value.
public DataPoint GetNewValue()
{
if(this.SelectedNode != null &&
this.SelectedNode.Tag != null &&
this.SelectedNode.Tag is DataPoint)
{
return (DataPoint)this.SelectedNode.Tag;
}
return null;
}
///
/// Mouse double clicked.
///
protected override void OnDoubleClick(EventArgs e)
{
base.OnDoubleClick(e);
if(this.edSvc != null)
{
if(GetNewValue() != null)
{
this.edSvc.CloseDropDown();
}
else if(this.SelectedNode != null &&
this.SelectedNode.Text == Constants.NotSetValue)
{
this.edSvc.CloseDropDown();
}
}
}
#endregion
}
///
/// UI type editor for the annotation axes.
///
public class AnnotationAxisUITypeEditor : System.Drawing.Design.UITypeEditor
{
#region Editor methods and properties
///
/// Display a dropdown list with check boxes.
///
/// Editing context.
/// Provider.
/// Value to edit.
/// Result
public override object EditValue(ITypeDescriptorContext context, IServiceProvider provider, object value)
{
if (context != null && context.Instance != null && provider != null)
{
IWindowsFormsEditorService edSvc = (IWindowsFormsEditorService)provider.GetService(typeof(IWindowsFormsEditorService));
if (edSvc != null &&
context.Instance is Annotation)
{
// Check if we dealing with X or Y axis
bool showXAxes = true;
if(context.PropertyDescriptor != null &&
context.PropertyDescriptor.Name == "AxisY")
{
showXAxes = false;
}
// Create control for editing
AnnotationAxisNameTreeView control = new AnnotationAxisNameTreeView(
edSvc,
(Annotation)context.Instance,
value as Axis,
showXAxes);
// Show drop down control
edSvc.DropDownControl(control);
// Get new enumeration value
value = control.GetNewValue();
// Dispose control
control.Dispose();
}
}
return value;
}
///
/// Gets editing style.
///
/// Editing context.
/// Editor style.
public override UITypeEditorEditStyle GetEditStyle(ITypeDescriptorContext context)
{
if (context != null && context.Instance != null)
{
return UITypeEditorEditStyle.DropDown;
}
return base.GetEditStyle(context);
}
#endregion
}
///
/// Annotation axes names tree view, which is used for the UI type editing.
///
internal class AnnotationAxisNameTreeView : System.Windows.Forms.TreeView
{
#region Control fields
// Annotation object to edit
private Annotation annotation = null;
private Axis axis = null;
IWindowsFormsEditorService edSvc = null;
private bool showXAxes = true;
#endregion
#region Control constructor
///
/// Public constructor.
///
/// Editor service.
/// Annotation to edit.
/// Axis object.
/// Indicates if X or Y axis should be shown.
public AnnotationAxisNameTreeView(
IWindowsFormsEditorService edSvc,
Annotation annotation,
Axis axis,
bool showXAxes)
{
// Set editable value
this.annotation = annotation;
this.axis = axis;
this.edSvc = edSvc;
this.showXAxes = showXAxes;
// Set control border style
this.BorderStyle = System.Windows.Forms.BorderStyle.None;
// Fill tree with data point names
this.FillTree();
}
#endregion
#region Control methods
///
/// Fills data points name tree.
///
private void FillTree()
{
bool nodeSelected = false;
this.BeginUpdate();
// Add "None" option
System.Windows.Forms.TreeNode noPoint = this.Nodes.Add(Constants.NotSetValue);
// Get chart object
if(this.annotation != null &&
annotation.GetAnnotationGroup() == null &&
this.annotation.Chart != null)
{
Chart chart = this.annotation.Chart;
// Loop through all chart areas
foreach(ChartArea chartArea in chart.ChartAreas)
{
System.Windows.Forms.TreeNode areaNode = this.Nodes.Add(chartArea.Name);
areaNode.Tag = chartArea;
// Loop through all axes
foreach(Axis curAxis in chartArea.Axes)
{
// Hide X or Y axes
if(curAxis.Type == AxisName.Y || curAxis.Type == AxisName.Y2)
{
if(showXAxes)
{
continue;
}
}
if(curAxis.Type == AxisName.X || curAxis.Type == AxisName.X2)
{
if(!showXAxes)
{
continue;
}
}
// Create child node
System.Windows.Forms.TreeNode axisNode = areaNode.Nodes.Add(curAxis.Name);
axisNode.Tag = curAxis;
// Check if this node should be selected
if(axis == curAxis)
{
areaNode.Expand();
this.SelectedNode = axisNode;
nodeSelected = true;
}
}
}
}
// Select default node
if(!nodeSelected)
{
this.SelectedNode = noPoint;
}
this.EndUpdate();
}
///
/// Gets a new data point.
///
/// New enum value.
public Axis GetNewValue()
{
if(this.SelectedNode != null &&
this.SelectedNode.Tag != null &&
this.SelectedNode.Tag is Axis)
{
return (Axis)this.SelectedNode.Tag;
}
return null;
}
///
/// Mouse double clicked.
///
protected override void OnDoubleClick(EventArgs e)
{
base.OnDoubleClick(e);
if(this.edSvc != null)
{
if(GetNewValue() != null)
{
this.edSvc.CloseDropDown();
}
else if(this.SelectedNode != null &&
this.SelectedNode.Text == Constants.NotSetValue)
{
this.edSvc.CloseDropDown();
}
}
}
#endregion
}
#endif // VS_DESIGN_TIME
#endif // !SMART_CLIENT
///
/// Converts anchor data point to string name.
///
public class AnchorPointValueConverter : TypeConverter
{
#region Converter methods
///
/// Converts anchor data point to string name.
///
/// Descriptor context.
/// Culture information.
/// Value to convert.
/// Conversion destination type.
/// Converted object.
public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
{
if (destinationType == typeof(string))
{
if(value == null)
{
return Constants.NotSetValue;
}
else if(value is DataPoint)
{
DataPoint dataPoint = (DataPoint)value;
if(dataPoint.series != null)
{
int pointIndex = dataPoint.series.Points.IndexOf(dataPoint) + 1;
return dataPoint.series.Name + " - " + SR.DescriptionTypePoint + pointIndex.ToString(CultureInfo.InvariantCulture);
}
}
}
// Call base class
return base.ConvertTo(context, culture, value, destinationType);
}
#endregion
}
///
/// Converts anchor data point to string name.
///
public class AnnotationAxisValueConverter : TypeConverter
{
#region Converter methods
///
/// Converts anchor data point to string name.
///
/// Descriptor context.
/// Culture information.
/// Value to convert.
/// Conversion destination type.
/// Converted object.
public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
{
if (destinationType == typeof(string))
{
if(value == null)
{
return Constants.NotSetValue;
}
else if(value is Axis)
{
Axis axis = (Axis)value;
if(axis.ChartArea != null)
{
return axis.ChartArea.Name + " - " + axis.Name;
}
}
}
// Call base class
return base.ConvertTo(context, culture, value, destinationType);
}
#endregion
}
}