private void refreshScalebar() { if (Map == null || double.IsNaN(Map.Resolution)) { this.Visibility = Visibility.Collapsed; return; } ScaleBarUnit outUnit = ScaleBarUnit.Undefined; double outResolution; #region KiloMeters/Meters double roundedKiloMeters = getBestEstimateOfValue(Map.Resolution, ScaleBarUnit.Kilometers, out outUnit, out outResolution); double widthMeters = roundedKiloMeters / outResolution; bool inMeters = outUnit == ScaleBarUnit.Meters; if (PaddingLeftForScaleBarTextMeters != null) { PaddingLeftForScaleBarTextMeters.Width = widthMeters; } if (PaddingLeftTopNotch != null) { PaddingLeftTopNotch.Width = widthMeters; } if (ScaleBarTextForMeters != null) { ScaleBarTextForMeters.Text = string.Format("{0}{1}", roundedKiloMeters, (inMeters ? "m" : "km")); ScaleBarTextForMeters.Width = widthMeters; } #endregion #region Miles double roundedMiles = getBestEstimateOfValue(Map.Resolution, ScaleBarUnit.Miles, out outUnit, out outResolution); double widthMiles = roundedMiles / outResolution; bool inFeet = outUnit == ScaleBarUnit.Feet; if (PaddingLeftForScaleBarTextMiles != null) { PaddingLeftForScaleBarTextMiles.Width = widthMiles; } if (PaddingLeftBottomNotch != null) { PaddingLeftBottomNotch.Width = widthMiles; } if (ScaleBarTextForMiles != null) { ScaleBarTextForMiles.Text = string.Format("{0}{1}", roundedMiles, inFeet ? "ft" : "mi"); ScaleBarTextForMiles.Width = widthMiles; } #endregion double widthOfNotches = 4; // 2 for left notch, 2 for right notch double scaleBarBlockWidth = (widthMiles > widthMeters) ? widthMiles : widthMeters; scaleBarBlockWidth += widthOfNotches; this.Visibility = roundedMiles == double.NaN || roundedKiloMeters == double.NaN ? Visibility.Collapsed : Visibility.Visible; if (!double.IsNaN(scaleBarBlockWidth) && ScaleBarBlock != null) { ScaleBarBlock.Width = scaleBarBlockWidth; } }
/// <summary> /// Constructor /// </summary> public LayoutScaleBar() { Name = "Scale Bar"; _font = new Font("Arial", 10); _color = Color.Black; _unit = ScaleBarUnit.Kilometers; _unitText = "km"; _numBreaks = 4; _textHint = TextRenderingHint.AntiAliasGridFit; ResizeStyle = ResizeStyle.HandledInternally; }
public double ConvertDistance(double distance, ScaleBarUnit toUnits) { double mDistance = distance; if (toUnits == ScaleBarUnit.Miles) { mDistance = distance / 1.60934; } else if (toUnits == ScaleBarUnit.Feet) { mDistance = distance * 3000.280839895; } else if (toUnits == ScaleBarUnit.Meters) { mDistance = distance * 1000; } return(mDistance); }
private double GetBestEstimateOfValue(double resolution, ScaleBarUnit displayUnit, out ScaleBarUnit unit, out double outResolution) { unit = displayUnit; double rounded = 0; double originalRes = resolution; while (rounded < 0.5) { resolution = originalRes; if (MapUnit == ScaleBarUnit.DecimalDegrees) { resolution = GetResolutionForGeographic(Map.Extent.GetCenter(), resolution); resolution = resolution * (int)ScaleBarUnit.Meters / (int)unit; } else if (webMercSref.Equals(Map.SpatialReference)) { //WebMercator MapPoint center = Map.Extent.GetCenter(); center.X = Math.Min(Math.Max(center.Y, -20037508.3427892), 20037508.3427892); MapPoint center2 = merc.ToGeographic(new MapPoint(Math.Min(center.X + Map.Resolution, 20037508.3427892), center.Y)) as MapPoint; center = merc.ToGeographic(center) as MapPoint; resolution = GetResolutionForGeographic(center, center2.X - center.X); resolution = resolution * (int)ScaleBarUnit.Meters / (int)unit; } else if (MapUnit != ScaleBarUnit.Undefined) { resolution = resolution * (int)MapUnit / (int)unit; } double val = TargetWidth * resolution; val = RoundToSignificant(val, resolution); double noFrac = Math.Round(val); // to get rid of the fraction if (val < 0.5) { ScaleBarUnit newUnit = ScaleBarUnit.Undefined; // Automatically switch unit to a lower one if (unit == ScaleBarUnit.Kilometers) newUnit = ScaleBarUnit.Meters; else if (unit == ScaleBarUnit.Miles) newUnit = ScaleBarUnit.Feet; if (newUnit == ScaleBarUnit.Undefined) { break; } //no lower unit unit = newUnit; } else if (noFrac > 1) { rounded = noFrac; var len = noFrac.ToString().Length; if (len <= 2) { // single/double digits ... make it a multiple of 5 ..or 1,2,3,4 if (noFrac > 5) { rounded -= noFrac % 5; } while (rounded > 1 && (rounded / resolution) > TargetWidth) { // exceeded maxWidth .. decrement by 1 or by 5 double decr = noFrac > 5 ? 5 : 1; rounded = rounded - decr; } } else if (len > 2) { rounded = Math.Round(noFrac / Math.Pow(10, len - 1)) * Math.Pow(10, len - 1); if ((rounded / resolution) > TargetWidth) { // exceeded maxWidth .. use the lower bound instead rounded = Math.Floor(noFrac / Math.Pow(10, len - 1)) * Math.Pow(10, len - 1); } } } else { // anything between 0.5 and 1 rounded = Math.Floor(val); if (rounded == 0) { //val >= 0.5 but < 1 so round up rounded = (val == 0.5) ? 0.5 : 1; if ((rounded / resolution) > TargetWidth) { // exceeded maxWidth .. re-try by switching to lower unit rounded = 0; ScaleBarUnit newUnit = ScaleBarUnit.Undefined; // Automatically switch unit to a lower one if (unit == ScaleBarUnit.Kilometers) newUnit = ScaleBarUnit.Meters; else if (unit == ScaleBarUnit.Miles) newUnit = ScaleBarUnit.Feet; if (newUnit == ScaleBarUnit.Undefined) { break; } //no lower unit unit = newUnit; } } } } outResolution = resolution; return rounded; }
/// <summary> /// Convert map units to scalebar units /// </summary> /// <param name="esriUnits">Map layer units</param> /// <returns>Scalebar units</returns> private ScaleBarUnit _ConvertScalebarUnits(ESRI.ArcLogistics.MapService.esriUnits esriUnits) { ScaleBarUnit scalebarUnits = ScaleBarUnit.Undefined; switch (esriUnits) { case ESRI.ArcLogistics.MapService.esriUnits.esriUnknownUnits: { scalebarUnits = ScaleBarUnit.Undefined; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriInches: { scalebarUnits = ScaleBarUnit.Inches; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriFeet: { scalebarUnits = ScaleBarUnit.Feet; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriYards: { scalebarUnits = ScaleBarUnit.Yards; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriMiles: { scalebarUnits = ScaleBarUnit.Miles; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriNauticalMiles: { scalebarUnits = ScaleBarUnit.NauticalMiles; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriMillimeters: { scalebarUnits = ScaleBarUnit.Millimeters; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriCentimeters: { scalebarUnits = ScaleBarUnit.Centimeters; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriMeters: { scalebarUnits = ScaleBarUnit.Meters; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriKilometers: { scalebarUnits = ScaleBarUnit.Kilometers; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriDecimalDegrees: { scalebarUnits = ScaleBarUnit.DecimalDegrees; break; } case ESRI.ArcLogistics.MapService.esriUnits.esriDecimeters: { scalebarUnits = ScaleBarUnit.Decimeters; break; } default: { Debug.Assert(false); break; } } return(scalebarUnits); }
/// <summary> /// Convert scalebar units to map scalebar units. /// </summary> /// <param name="scaleBarUnits">Scalebar units.</param> /// <returns>Scalebar map units.</returns> public static ESRI.ArcGIS.Client.ScaleBarUnit ConvertScalebarUnits(ScaleBarUnit scaleBarUnits) { ESRI.ArcGIS.Client.ScaleBarUnit mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Undefined; switch (scaleBarUnits) { case ScaleBarUnit.Undefined: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Undefined; break; } case ScaleBarUnit.Inches: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Inches; break; } case ScaleBarUnit.Feet: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Feet; break; } case ScaleBarUnit.Yards: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Yards; break; } case ScaleBarUnit.Miles: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Miles; break; } case ScaleBarUnit.NauticalMiles: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.NauticalMiles; break; } case ScaleBarUnit.Millimeters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Millimeters; break; } case ScaleBarUnit.Centimeters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Centimeters; break; } case ScaleBarUnit.Meters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Meters; break; } case ScaleBarUnit.Kilometers: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Kilometers; break; } case ScaleBarUnit.DecimalDegrees: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.DecimalDegrees; break; } case ScaleBarUnit.Decimeters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Decimeters; break; } default: { Debug.Assert(false); break; } } return(mapScalebarUnits); }
private double getBestEstimateOfValue(double resolution, ScaleBarUnit displayUnit, out ScaleBarUnit unit, out double outResolution) { unit = displayUnit; double rounded = 0; double originalRes = resolution; while (rounded < 0.5) { resolution = originalRes; if (MapUnit == ScaleBarUnit.DecimalDegrees) { resolution = getResolutionForGeographic(Map.Extent, resolution); resolution = resolution * (int)ScaleBarUnit.Meters / (int)unit; } else if (MapUnit != ScaleBarUnit.Undefined) { resolution = resolution * (int)MapUnit / (int)unit; } double val = TargetWidth * resolution; val = roundToSignificant(val, resolution); double noFrac = Math.Round(val); // to get rid of the fraction if (val < 0.5) { ScaleBarUnit newUnit = ScaleBarUnit.Undefined; // Automatically switch unit to a lower one if (unit == ScaleBarUnit.Kilometers) { newUnit = ScaleBarUnit.Meters; } else if (unit == ScaleBarUnit.Miles) { newUnit = ScaleBarUnit.Feet; } if (newUnit == ScaleBarUnit.Undefined) { break; } //no lower unit unit = newUnit; } else if (noFrac > 1) { rounded = noFrac; var len = noFrac.ToString().Length; if (len <= 2) { // single/double digits ... make it a multiple of 5 ..or 1,2,3,4 if (noFrac > 5) { rounded -= noFrac % 5; } while (rounded > 1 && (rounded / resolution) > TargetWidth) { // exceeded maxWidth .. decrement by 1 or by 5 double decr = noFrac > 5 ? 5 : 1; rounded = rounded - decr; } } else if (len > 2) { rounded = Math.Round(noFrac / Math.Pow(10, len - 1)) * Math.Pow(10, len - 1); if ((rounded / resolution) > TargetWidth) { // exceeded maxWidth .. use the lower bound instead rounded = Math.Floor(noFrac / Math.Pow(10, len - 1)) * Math.Pow(10, len - 1); } } } else { // anything between 0.5 and 1 rounded = Math.Floor(val); if (rounded == 0) { //val >= 0.5 but < 1 so round up rounded = (val == 0.5) ? 0.5 : 1; if ((rounded / resolution) > TargetWidth) { // exceeded maxWidth .. re-try by switching to lower unit rounded = 0; ScaleBarUnit newUnit = ScaleBarUnit.Undefined; // Automatically switch unit to a lower one if (unit == ScaleBarUnit.Kilometers) { newUnit = ScaleBarUnit.Meters; } else if (unit == ScaleBarUnit.Miles) { newUnit = ScaleBarUnit.Feet; } if (newUnit == ScaleBarUnit.Undefined) { break; } //no lower unit unit = newUnit; } } } } outResolution = resolution; return(rounded); }
private void refreshScalebar() { Visibility viz = Visibility.Visible; if (Map == null || double.IsNaN(Map.Resolution) || MapUnit == ScaleBarUnit.DecimalDegrees && Math.Abs(Map.Extent.GetCenter().Y) >= 90) { viz = Visibility.Collapsed; } if (LayoutRoot != null) { LayoutRoot.Visibility = viz; } if (viz == Visibility.Collapsed) { return; } ScaleBarUnit outUnit = ScaleBarUnit.Undefined; double outResolution; #region KiloMeters/Meters double roundedKiloMeters = getBestEstimateOfValue(Map.Resolution, ScaleBarUnit.Kilometers, out outUnit, out outResolution); double widthMeters = roundedKiloMeters / outResolution; bool inMeters = outUnit == ScaleBarUnit.Meters; if (PaddingLeftForScaleBarTextMeters != null) { PaddingLeftForScaleBarTextMeters.Width = widthMeters; } if (PaddingLeftTopNotch != null) { PaddingLeftTopNotch.Width = widthMeters; } if (ScaleBarTextForMeters != null) { ScaleBarTextForMeters.Text = string.Format("{0}{1}", roundedKiloMeters, (inMeters ? "m" : "km")); ScaleBarTextForMeters.Width = widthMeters; } #endregion #region Miles double roundedMiles = getBestEstimateOfValue(Map.Resolution, ScaleBarUnit.Miles, out outUnit, out outResolution); double widthMiles = roundedMiles / outResolution; bool inFeet = outUnit == ScaleBarUnit.Feet; if (PaddingLeftForScaleBarTextMiles != null) { PaddingLeftForScaleBarTextMiles.Width = widthMiles; } if (PaddingLeftBottomNotch != null) { PaddingLeftBottomNotch.Width = widthMiles; } if (ScaleBarTextForMiles != null) { ScaleBarTextForMiles.Text = string.Format("{0}{1}", roundedMiles, inFeet ? "ft" : "mi"); ScaleBarTextForMiles.Width = widthMiles; } #endregion double widthOfNotches = 4; // 2 for left notch, 2 for right notch double scaleBarBlockWidth = (widthMiles > widthMeters) ? widthMiles : widthMeters; scaleBarBlockWidth += widthOfNotches; if (!double.IsNaN(scaleBarBlockWidth) && ScaleBarBlock != null) { ScaleBarBlock.Width = scaleBarBlockWidth; } }
/// <summary> /// Convert scalebar units to map scalebar units. /// </summary> /// <param name="scaleBarUnits">Scalebar units.</param> /// <returns>Scalebar map units.</returns> public static ESRI.ArcGIS.Client.ScaleBarUnit ConvertScalebarUnits(ScaleBarUnit scaleBarUnits) { ESRI.ArcGIS.Client.ScaleBarUnit mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Undefined; switch (scaleBarUnits) { case ScaleBarUnit.Undefined: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Undefined; break; } case ScaleBarUnit.Inches: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Inches; break; } case ScaleBarUnit.Feet: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Feet; break; } case ScaleBarUnit.Yards: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Yards; break; } case ScaleBarUnit.Miles: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Miles; break; } case ScaleBarUnit.NauticalMiles: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.NauticalMiles; break; } case ScaleBarUnit.Millimeters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Millimeters; break; } case ScaleBarUnit.Centimeters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Centimeters; break; } case ScaleBarUnit.Meters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Meters; break; } case ScaleBarUnit.Kilometers: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Kilometers; break; } case ScaleBarUnit.DecimalDegrees: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.DecimalDegrees; break; } case ScaleBarUnit.Decimeters: { mapScalebarUnits = ESRI.ArcGIS.Client.ScaleBarUnit.Decimeters; break; } default: { Debug.Assert(false); break; } } return mapScalebarUnits; }