// (c) Copyright ESRI. // This source is subject to the Microsoft Public License (Ms-PL). // Please see http://go.microsoft.com/fwlink/?LinkID=131993 for details. // All other rights reserved. using System.Collections.Generic; using System.Windows; using System.Windows.Controls; using System.Windows.Input; using System.Windows.Media; using System.Windows.Shapes; using ESRI.ArcGIS.Client.Symbols; using System.ComponentModel; using System; using System.Windows.Markup; namespace ESRI.ArcGIS.Client.Toolkit.Primitives { /// /// A control that displays a symbol presenter scaled to fit. /// [System.ComponentModel.EditorBrowsable(System.ComponentModel.EditorBrowsableState.Never)] public class SymbolDisplay : Control { DataBinder data = new DataBinder(); private ContentPresenter ChildElement { get; set; } private ScaleTransform Scale { get; set; } SymbolPresenter presenter = new SymbolPresenter(); /// /// The symbol presenter /// public SymbolPresenter SymbolContent { get { return presenter; } } /// /// Constructor. /// public SymbolDisplay() { string temp = ""; #if SILVERLIGHT Template = System.Windows.Markup.XamlReader.Load(temp) as ControlTemplate; #else System.IO.MemoryStream templateStream = new System.IO.MemoryStream(System.Text.UTF8Encoding.Default.GetBytes(temp)); Template = System.Windows.Markup.XamlReader.Load(templateStream) as ControlTemplate; #endif ApplyTemplate(); base.IsTabStop = false; } /// /// Overrides OnApplyTemplate /// public override void OnApplyTemplate() { this.ChildElement = base.GetTemplateChild("Child") as ContentPresenter; this.ChildElement.RenderTransform = this.Scale = new ScaleTransform(); this.ChildElement.Content = presenter; this.SymbolContent.DataContext = data; } /// /// The symbol to display /// public Symbol Symbol { get { return (Symbol)GetValue(SymbolProperty); } set { SetValue(SymbolProperty, value); } } /// /// Overrides MeasureOverride /// /// /// protected override Size MeasureOverride(Size availableSize) { Size size = new Size(); if (this.ChildElement != null) { this.ChildElement.Measure((Symbol is MarkerSymbol) ? new Size(double.PositiveInfinity, double.PositiveInfinity) : availableSize); Size desiredSize = this.ChildElement.DesiredSize; double factor = ComputeScaleFactor(availableSize, desiredSize); size.Width = desiredSize.Width * factor; size.Height = desiredSize.Height * factor; } return size; } private static double ComputeScaleFactor(Size availableSize, Size desiredSize) { return Math.Min(1, Math.Min(availableSize.Width / desiredSize.Width, availableSize.Height / desiredSize.Height)); } /// /// Overrides ArrangeOverride /// /// /// protected override Size ArrangeOverride(Size finalSize) { if (this.ChildElement != null) { Size desiredSize = this.ChildElement.DesiredSize; double factor = ComputeScaleFactor(finalSize, desiredSize); this.Scale.ScaleX = factor; this.Scale.ScaleY = factor; Rect finalRect = new Rect(0.0, 0.0, desiredSize.Width, desiredSize.Height); this.ChildElement.Arrange(finalRect); finalSize.Width = factor * desiredSize.Width; finalSize.Height = factor * desiredSize.Height; } return finalSize; } /// /// Identifies the dependency property. /// public static readonly DependencyProperty SymbolProperty = DependencyProperty.Register("Symbol", typeof(Symbol), typeof(SymbolDisplay), new PropertyMetadata(OnSymbolPropertyChanged)); private static void OnSymbolPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) { SymbolDisplay obj = (SymbolDisplay)d; obj.SymbolContent.Symbol = obj.data.Symbol = e.NewValue as Symbol; } /// /// The attributes. Required for data binding /// public Dictionary Attributes { get { return (Dictionary)GetValue(AttributesProperty); } set { SetValue(AttributesProperty, value); } } /// /// Identifies the dependency property. /// public static readonly DependencyProperty AttributesProperty = DependencyProperty.Register("Attributes", typeof(IDictionary), typeof(SymbolDisplay), new PropertyMetadata(null, OnAttributesPropertyChanged)); private static void OnAttributesPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) { SymbolDisplay obj = (SymbolDisplay)d; obj.data.Attributes = (IDictionary)e.NewValue; } /// /// The data binder. Used for data binding. /// public class DataBinder : INotifyPropertyChanged { IDictionary attributes; /// /// Attributes /// public IDictionary Attributes { get { return attributes; } set { attributes = value; if (PropertyChanged != null) PropertyChanged(this, new PropertyChangedEventArgs("Attributes")); } } Symbol symbol; /// /// Symbol /// public Symbol Symbol { get { return symbol; } set { symbol = value; if (PropertyChanged != null) PropertyChanged(this, new PropertyChangedEventArgs("Symbol")); } } #region INotifyPropertyChanged Members /// /// Property changed event. /// public event PropertyChangedEventHandler PropertyChanged; #endregion } } }