public static ImageInfo getIcon(String symbolID, int size, Color color, int outlineSize)
        {
            ImageInfo returnVal = null;
            if (_tgl == null)
                _tgl = TacticalGraphicLookup.getInstance();

            int mapping = _tgl.getCharCodeFromSymbol(symbolID);

            CanvasRenderTarget coreBMP = null;

            SVGPath svgTG = null;
            //SVGPath svgFrame = null;

            if (mapping > 0)
                svgTG = TGSVGTable.getInstance().getSVGPath(mapping);

            //float scale = 1;
            Matrix3x2 mScale, mTranslate;
            Matrix3x2 mIdentity = Matrix3x2.Identity;
            Rect rectF = new Rect();
            Matrix3x2 m = svgTG.CreateMatrix(size, size, out rectF, out mScale, out mTranslate);
            //svgTG.TransformToFitDimensions(size, size);
            Rect rr = svgTG.computeBounds(m);
            
            CanvasDevice device = CanvasDevice.GetSharedDevice();
            //CanvasRenderTarget offscreen = new CanvasRenderTarget(device, width, height, 96);
            coreBMP = new CanvasRenderTarget(device, (int)(rr.Width + 0.5), (int)(rr.Height + 0.5),96);

            using (CanvasDrawingSession cds = coreBMP.CreateDrawingSession())
            {
                svgTG.Draw(cds, Colors.Transparent, 0, color, m);
                cds.DrawRectangle(coreBMP.GetBounds(device), Colors.Red);
            }
            returnVal = new ImageInfo(coreBMP,new Point(coreBMP.Size.Width/2f,coreBMP.Size.Height/2.0f),new Rect(0,0,coreBMP.Size.Width,coreBMP.Size.Height),coreBMP.GetBounds(device));

            return returnVal;
        }
 /// <summary>
 /// 
 /// </summary>
 /// <param name="symbolID"></param>
 /// <param name="msb"></param>
 /// <param name="modifiers"></param>
 /// <param name="attributes"></param>
 /// <returns></returns>
 private ImageInfo ProcessUnitDisplayModifiers(String symbolID, ImageInfo msb, Dictionary<String, String> modifiers, Dictionary<String, String> attributes)
 {
     try
     {
     }
     catch (Exception exc)
     {
         ErrorLogger.LogException("SinglePointRenderer", "ProcessUnitDisplayModifiers", exc);
         return null;
     }
     return null;
 }
        /// <summary>
        /// 
        /// </summary>
        /// <param name="symbolID"></param>
        /// <param name="modifiers"></param>
        /// <param name="attributes"></param>
        /// <returns></returns>
        public ImageInfo RenderUnit(String symbolID, Dictionary<int,String> modifiers, Dictionary<int,String> attributes, CanvasDevice device)
        {
            //L 1.5 = 2650 pixel units in the svg font file
            double L1_5 = 2650;
            CanvasRenderTarget finalBMP = null;

            CanvasRenderTarget coreBMP = null;
            try
            {

                //get font character indexes
                int fillIndex = -1;
                int frameIndex = -1;
                int symbol1Index = -1;
                int symbol2Index = -1;
                SVGPath svgFill = null;
                SVGPath svgFrame = null;
                SVGPath svgSymbol1 = null;
                SVGPath svgSymbol2 = null;

                //get attributes
                int alpha = 255;
                Boolean drawAsIcon = false;
                Boolean keepUnitRatio = true;
                int pixelSize = 0;
                Color fillColor = SymbolUtilities.getFillColorOfAffiliation(symbolID);
                Color frameColor = SymbolUtilities.getLineColorOfAffiliation(symbolID);

                if (attributes == null)
                    attributes = new Dictionary<int, string>();
                if (attributes.ContainsKey(MilStdAttributes.LineColor))
                    frameColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.LineColor]);

                if (attributes.ContainsKey(MilStdAttributes.FillColor))
                    fillColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.FillColor]);

                if (attributes.ContainsKey(MilStdAttributes.Alpha))
                    alpha = Convert.ToInt32(attributes[MilStdAttributes.Alpha]);

                if (attributes.ContainsKey(MilStdAttributes.DrawAsIcon))
                    drawAsIcon = Convert.ToBoolean(attributes[MilStdAttributes.DrawAsIcon]);

                if (attributes.ContainsKey(MilStdAttributes.PixelSize))
                    pixelSize = Convert.ToInt32(attributes[MilStdAttributes.PixelSize]);
                else
                    pixelSize = 35;

                if (attributes.ContainsKey(MilStdAttributes.KeepUnitRatio))
                    keepUnitRatio = Convert.ToBoolean(attributes[MilStdAttributes.KeepUnitRatio]);

                String basicID = SymbolUtilities.getBasicSymbolIDStrict(symbolID);
                UnitFontLookupInfo ufli = UnitFontLookup.getInstance().getLookupInfo(basicID);
                fillIndex = UnitFontLookup.getFillCode(symbolID);
                frameIndex = UnitFontLookup.getFrameCode(symbolID, fillIndex);
                if (ufli != null)
                {
                    symbol1Index = ufli.getMapping1(symbolID);
                    symbol2Index = ufli.getMapping2();
                }

                if (fillIndex > 0)
                    svgFill = UnitSVGTable.getInstance().getSVGPath(fillIndex);
                if (frameIndex > 0)
                    svgFrame = UnitSVGTable.getInstance().getSVGPath(frameIndex);
                if (symbol1Index > 0)
                    svgSymbol1 = UnitSVGTable.getInstance().getSVGPath(symbol1Index);
                if (symbol2Index > 0)
                    svgSymbol2 = UnitSVGTable.getInstance().getSVGPath(symbol2Index);


                //get dimensions for this symbol given the font size & fill index


                Matrix3x2 matrix = new Matrix3x2();
                double heightL = 1;
                double widthL = 1;

                Rect rectFrame = svgFrame.getBounds();
                if (keepUnitRatio)
                {
                    double ratio = pixelSize / L1_5 / 1.5;
                    widthL = UnitFontLookup.getUnitRatioWidth(fillIndex);
                    heightL = UnitFontLookup.getUnitRatioHeight(fillIndex);
                    if (widthL > heightL)
                        ratio = ratio * widthL;
                    else
                        ratio = ratio * heightL;
                    pixelSize = (int)((ratio * L1_5) + 0.5);

                }

                Matrix3x2 mScale, mTranslate;
                Matrix3x2 mIdentity = Matrix3x2.Identity;
                Rect rectF = new Rect();
                matrix = svgFrame.CreateMatrix(pixelSize, pixelSize, out rectF, out mScale, out mTranslate);


                //int w = (int)(rectF.Width + 1.5f);
                //int h = (int)(rectF.Height + 1.5f);
                int w = (int)(rectF.Width);
                int h = (int)(rectF.Height);
                if (w == pixelSize && h != pixelSize)
                    h = (int)Math.Ceiling(rectF.Height);
                else if (h == pixelSize && w != pixelSize)
                    w = (int)Math.Ceiling(rectF.Width);

                bool bufferUsed = false;
                if(w < coreBufferSize && h < coreBufferSize)
                {
                    if(coreUnitBuffer == null)
                    {
                        if (device == null)
                            device = CanvasDevice.GetSharedDevice();
                        coreUnitBuffer = new CanvasRenderTarget(device, coreBufferSize, coreBufferSize, 96);//new Bitmap(w, h);
                    }
                    coreBMP = coreUnitBuffer;
                    bufferUsed = true;
                }
                else
                {
                    if (device == null)
                        device = CanvasDevice.GetSharedDevice();
                    coreBMP = new CanvasRenderTarget(device, w, h, 96);//new Bitmap(w, h);
                }
                Point centerPoint = new Point(w / 2, h / 2);

                //get & setup graphics object for destination BMP
                
                using (CanvasDrawingSession ds = coreBMP.CreateDrawingSession())
                {
                    ds.Clear(Colors.Transparent);
                    //clear canvas
                    //ds.Transform = matrix;
                    // ds.Transform = mScale;
                    //draw symbol to BMP
                   // ds.Transform = mScale * mTranslate;
                    if (svgFill != null)
                    {
                        //svgFill.Transform(mScale);
                        //svgFill.Transform(mTranslate);
                        svgFill.Draw(ds, Colors.Transparent, 0, fillColor, matrix);
                    }
                    if (svgFrame != null)
                    {
                        svgFrame.Draw(ds, Colors.Transparent, 0, frameColor, matrix);
                    }
                    if (svgSymbol2 != null)
                    {
                        //svgSymbol2.Transform(mScale);
                        //svgSymbol2.Transform(mTranslate);
                        svgSymbol2.Draw(ds, Colors.Transparent, 0, ufli.getColor2(), matrix);
                    }
                    if (svgSymbol1 != null)
                    {
                        //svgSymbol1.Transform(mScale);
                        //svgSymbol1.Transform(mTranslate);
                        svgSymbol1.Draw(ds, Colors.Transparent, 0, ufli.getColor1(), matrix);
                    }
                    //ds.Transform = Matrix3x2.Identity;
                }//*/
                /*
                if (svgFill != null)
                {
                    svgFill.Transform(mScale);
                    svgFill.Transform(mTranslate);
                    //svgFill.Transform(matrix);
                    svgFill.Draw(coreBMP, Colors.Transparent, 0, fillColor, mIdentity);
                }
                if (svgFrame != null)
                {
                    svgFrame.Draw(coreBMP, Colors.Transparent, 0, frameColor, mIdentity);
                }
                if (svgSymbol2 != null)
                {
                    svgSymbol2.Transform(mScale);
                    svgSymbol2.Transform(mTranslate);
                    svgSymbol2.Draw(coreBMP, Colors.Transparent, 0, ufli.getColor2(), mIdentity);
                }
                if (svgSymbol1 != null)
                {
                    svgSymbol1.Transform(mScale);
                    svgSymbol1.Transform(mTranslate);
                    svgSymbol1.Draw(coreBMP, Colors.Transparent, 0, ufli.getColor1(), mIdentity);
                }//*/
                Rect coreDimensions = new Rect(0, 0, w, h);
                Rect finalDimensions = new Rect(0, 0, w, h);

                //adjust centerpoint for HQStaff if present
				if(SymbolUtilities.isHQ(symbolID))
				{
					Point point1 = new Point();
					Point point2 = new Point();
					string affiliation = symbolID.Substring(1, 2);
					if(affiliation==("F") ||
						affiliation==("A") ||
						affiliation==("D") ||
						affiliation==("M") ||
						affiliation==("J") ||
						affiliation==("K") ||
						affiliation==("N") ||
						affiliation==("L"))
					{
						point1.X = 0;
                        point1.Y = (coreBMP.Size.Height);
						point2.X = point1.X;
                        point2.Y = point1.Y + coreBMP.Size.Height;
					}
					else
					{
						point1.X = 1;
                        point1.Y = (coreBMP.Size.Height / 2);
						point2.X = point1.X;
                        point2.Y = point1.Y + coreBMP.Size.Height;
					}
					centerPoint = point2;
				}


                if (device == null)
                    device = CanvasDevice.GetSharedDevice();
                finalBMP = new CanvasRenderTarget(device, (float)finalDimensions.Width, (float)finalDimensions.Height, 96);

                ImageInfo ii = new ImageInfo(coreBMP, new Point(centerPoint.X, centerPoint.Y), new Rect(0, 0, coreBMP.Size.Width, coreBMP.Size.Height),coreBMP.GetBounds(device));
                

                //process display modifiers
                ImageInfo iinew = null;

                Boolean hasDisplayModifiers = ModifierRenderer.hasDisplayModifiers(symbolID, modifiers);
                Boolean hasTextModifiers = ModifierRenderer.hasTextModifiers(symbolID, modifiers, attributes);
                if (hasDisplayModifiers)
                {
                    //iinew = ModifierRenderer.ProcessUnitDisplayModifiers(symbolID, ii, modifiers, attributes, true);
                }//*/

                if (iinew != null)
                {
                    ii = iinew;
                }
                iinew = null;

                //process text modifiers
                if (hasTextModifiers)
                {
                    //iinew = ModifierRenderer.ProcessUnitTextModifiers(ii, symbolID, modifiers, attributes);
                }//*/

                if (iinew != null)
                {
                    ii = iinew;
                }
                iinew = null;


                //////
                svgFill = null;
                svgFrame = null;
                svgSymbol1 = null;
                svgSymbol2 = null;
                device = null;
                //if(bufferUsed==false)
                //    coreBMP.Dispose();
                coreBMP = null;
                finalBMP = null;
                return ii;
            }
            catch (Exception exc)
            {
                ErrorLogger.LogException("SinglePointRenderer", "RenderUnit", exc);
                return null;
            }
        }
        public ImageInfo RenderSPTG(String symbolID, Dictionary<int,String> modifiers, Dictionary<int,String> attributes)
        {
            if (modifiers == null)
                modifiers = new Dictionary<int, string>();
            if (attributes == null)
                attributes = new Dictionary<int, string>();
            CanvasRenderTarget finalBmp = null;

            CanvasRenderTarget coreBMP = null;
            try
            {
                //get font character indexes (svg file for this renderer port)
                int fillIndex = -1;
                int frameIndex = -1;

                int alpha = 255;

                int symbolOutlineSize = 0;
                Color symbolOutlineColor = Colors.Transparent;
                Boolean drawAsIcon = false;
                Boolean keepUnitRatio = true;
                int pixelSize = 35;
                int w = pixelSize;
                int h = pixelSize;

                char[] fillString = new char[1];
                char[] frameString = new char[1];
                char[] symbol1 = new char[1];
                char[] symbol2 = new char[1];

                
                //_spFontSize;
                Color lineColor = Colors.Transparent;
                Color fillColor = Colors.Transparent;

                if (attributes.ContainsKey(MilStdAttributes.LineColor))
                    lineColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.LineColor]);
                else
                    lineColor = SymbolUtilities.getLineColorOfAffiliation(symbolID);

                if(attributes.ContainsKey(MilStdAttributes.FillColor))
                    fillColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.FillColor]);

                if (attributes.ContainsKey(MilStdAttributes.Alpha))
                    alpha = Convert.ToInt32(attributes[MilStdAttributes.Alpha]);

                if (attributes.ContainsKey(MilStdAttributes.SymbolOutlineColor))
                    symbolOutlineColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.SymbolOutlineColor]);
                else
                    symbolOutlineColor = RenderUtilities.getIdealTextBackgroundColor(lineColor);

                if (attributes.ContainsKey(MilStdAttributes.SymbolOutlineSize))
                    symbolOutlineSize = Convert.ToInt32(attributes[MilStdAttributes.SymbolOutlineSize]);
                else
                    symbolOutlineSize = RendererSettings.getInstance().getSymbolOutlineWidth();
                
                if (symbolOutlineSize <= 0)
                    symbolOutlineColor = Colors.Transparent;

                if (attributes.ContainsKey(MilStdAttributes.DrawAsIcon))
                    drawAsIcon = Convert.ToBoolean(attributes[MilStdAttributes.DrawAsIcon]);

                if (attributes.ContainsKey(MilStdAttributes.PixelSize))
                    pixelSize = Convert.ToInt32(attributes[MilStdAttributes.PixelSize]);

                if (attributes.ContainsKey(MilStdAttributes.KeepUnitRatio))
                    keepUnitRatio = Convert.ToBoolean(attributes[MilStdAttributes.KeepUnitRatio]);

                SinglePointLookupInfo spli = SinglePointLookup.getInstance().getSPLookupInfo(SymbolUtilities.getBasicSymbolIDStrict(symbolID));

                if (spli == null)//default to action point on bad symbolID
                {
                    if (modifiers == null)
                        modifiers = new Dictionary<int, string>();
                    if (modifiers.ContainsKey(ModifiersTG.H_ADDITIONAL_INFO_1))
                        modifiers[ModifiersTG.H1_ADDITIONAL_INFO_2] = modifiers[ModifiersTG.H_ADDITIONAL_INFO_1];
                    modifiers[ModifiersTG.H_ADDITIONAL_INFO_1] = symbolID.Substring(0, 10);

                    symbolID = "G" + SymbolUtilities.getAffiliation(symbolID) +
                        "G" + SymbolUtilities.getStatus(symbolID) + "GPP---****X";
                    spli = SinglePointLookup.getInstance().getSPLookupInfo(symbolID);
                    lineColor = SymbolUtilities.getLineColorOfAffiliation(symbolID);
                    //fillColor = SymbolUtilities.getFillColorOfAffiliation(symbolID);
                }

                //Check if we need to set 'N' to ENY

                if (symbolID[1] == 'H' && drawAsIcon == false)
                {
                    if (modifiers == null)
                        modifiers = new Dictionary<int, string>();
                    modifiers[ModifiersTG.N_HOSTILE] = "ENY";
                }

                if (SymbolUtilities.getStatus(symbolID) == "A")
                    frameIndex = spli.getMappingA();
                else
                    frameIndex = spli.getMappingP();

                if (SymbolUtilities.isTGSPWithFill(symbolID))
                {
                    String fillID = SymbolUtilities.getTGFillSymbolCode(symbolID);
                    if (fillID != null)
                        fillIndex = SinglePointLookup.getInstance().getCharCodeFromFillID(fillID);
                }
                else if (SymbolUtilities.isWeatherSPWithFill(symbolID))
                {
                    fillIndex = frameIndex + 1;
                    fillColor = SymbolUtilities.getFillColorOfWeather(symbolID);

                }
                   

                fillString[0] = (char)fillIndex;
                frameString[0] = (char)frameIndex;


                SVGPath svgFill = null;
                SVGPath svgFrame = null;

                if(fillIndex > 0)
                    svgFill = SymbolSVGTable.getInstance().getSVGPath(fillIndex);
                if(frameIndex > 0)
                    svgFrame = SymbolSVGTable.getInstance().getSVGPath(frameIndex);
                
                float scale = 1;
                Rect rr = svgFrame.getBounds();

                if (keepUnitRatio)
                {
                    scale = pixelSize * 1f;
                    if (rr.Height > rr.Width)
                        pixelSize = (int)((scale * rr.Height) + 0.5);
                    else
                        pixelSize = (int)((scale * rr.Width) + 0.5);
                }

                Matrix3x2 mScale, mTranslate;
                Matrix3x2 mIdentity = Matrix3x2.Identity;
                Rect rectF = new Rect();
                Matrix3x2  m = svgFrame.CreateMatrix(pixelSize, pixelSize, out rectF, out mScale, out mTranslate);
                //Matrix3x2 m = svgFrame.TransformToFitDimensions(pixelSize, pixelSize);

                rr = svgFrame.computeBounds(m);
                w = (int)((rr.Width) + 0.5f);
                h = (int)((rr.Height) + 0.5f);
                //draw location
                Point centerPoint = SymbolDimensions.getSymbolCenter(spli.getBasicSymbolID(), rr);
                Point location = new Point(0, 0);

                location.X = centerPoint.X;
                location.Y = 0;// centerPoint.Y;
                //location.Y = (h * 1.5f);

                float outlineOffsetX = 0;
                float outlineOffsetY = 0;
                Matrix3x2 mOutline = new Matrix3x2();

                CanvasDevice device = CanvasDevice.GetSharedDevice();
                //CanvasRenderTarget offscreen = new CanvasRenderTarget(device, width, height, 96);

                if (symbolOutlineSize > 0)
                {
                    Rect rectOutline = ShapeUtilities.inflate(rr, symbolOutlineSize, symbolOutlineSize);// svgFrame.getBounds(symbolOutlineSize);
                    outlineOffsetX = (float)((rectOutline.Width - w) / 2f );
                    outlineOffsetY = (float)((rectOutline.Height - h) / 2f );//too much added for AA
                    w = (int)(rectOutline.Width + 0.5f);
                    h = (int)(rectOutline.Height + 0.5f);
                    mOutline = Matrix3x2.CreateTranslation(outlineOffsetX, outlineOffsetY);
                    centerPoint.X += outlineOffsetX;
                    centerPoint.Y += outlineOffsetY;
                    coreBMP = new CanvasRenderTarget(device, w, h,96);// new Bitmap(w, h);//getBounds adds too much for AA
                }
                else
                {
                    coreBMP = new CanvasRenderTarget(device, w, h, 96);//add for AA
                }
                //coreBMP = new Bitmap(w, h);
                
                //draw test outline
                //g.DrawRectangle(new Pen(Color.LightSkyBlue), 0, 0, coreBMP.Width - 1, coreBMP.Height - 1);
                using (CanvasDrawingSession cds = coreBMP.CreateDrawingSession())
                {
                    if (svgFill != null)
                    {
                        svgFill.Transform(m);
                        svgFill.Draw(cds, Colors.Transparent, 0, fillColor, mOutline);
                    }

                    if (svgFrame != null)
                    {
                        svgFrame.Transform(m);
                        svgFrame.Draw(cds, symbolOutlineColor, symbolOutlineSize, lineColor, mOutline);
                    }
                        

                    cds.DrawRectangle(new Rect(0, 0, (int)(coreBMP.Size.Width + 0.5f), (int)(coreBMP.Size.Height + 0.5f)), Colors.Red);
                }


                Rect coreDimensions = new Rect(0, 0, (int)(coreBMP.Size.Width + 0.5f), (int)(coreBMP.Size.Height + 0.5f));
                
                ImageInfo ii = new ImageInfo(coreBMP, centerPoint, coreDimensions,coreBMP.GetBounds(device));

                //process display modifiers
                Boolean hasDisplayModifiers = ModifierRenderer.hasDisplayModifiers(symbolID, modifiers);
                Boolean hasTextModifiers = ModifierRenderer.hasTextModifiers(symbolID, modifiers, attributes);
                ImageInfo iinew = null;

                /*Boolean hasDisplayModifiers = ModifierRenderer.hasDisplayModifiers(symbolID, modifiers);
                Boolean hasTextModifiers = ModifierRenderer.hasTextModifiers(symbolID, modifiers, attributes);
                if (hasDisplayModifiers)
                {
                    iinew = ModifierRenderer.ProcessUnitDisplayModifiers(symbolID, ii, modifiers, attributes, true);
                }//*/

                if (iinew != null)
                {
                    ii = iinew;
                }
                iinew = null;

                //process text modifiers
                /*if (hasTextModifiers)
                {
                    //iinew = ModifierRenderer.ProcessUnitTextModifiers(symbolID, ii, modifiers, attributes);
                    iinew = ModifierRenderer.ProcessUnitTextModifiers(ii, symbolID, modifiers, attributes);
                }//*/

                if (iinew != null)
                {
                    ii = iinew;
                }
                iinew = null;

                /*if (coreBMP != null)
                {
                    coreBMP.Dispose();
                    coreBMP = null;
                }//*/

                return ii;
            }
            catch (Exception exc)
            {
                ErrorLogger.LogException("SinglePointRenderer", "RenderSPTG", exc);
                return null;
            }
        }
        //private static Bitmap _textBMP = new Bitmap(2, 2);
        //private static Graphics _g = Graphics.FromImage(_textBMP);
        //private static Matrix _identityMatrix = new Matrix();
        //private static int _fontSize = RS.getModifierFontSize();
        //private static FontStyle _fontStyle = RS.getModifierFontStyle();
        //private static String _fontName = RS.getModifierFontName();
        //private static int _modifierFontHeight = ShapeUtilities.round(_g.MeasureString("Hj", RS.getLabelFont()).Height);
        //private static Font _modifierFont = RS.getLabelFont();

        /// <summary>
        /// 
        /// </summary>
        /// <param name="symbolID"></param>
        /// <param name="msb"></param>
        /// <param name="modifiers"></param>
        /// <param name="attributes"></param>
        /// <returns></returns>
        public static ImageInfo ProcessUnitDisplayModifiers(String symbolID, ImageInfo ii, Dictionary<int, String> modifiers, Dictionary<int, String> attributes, Boolean hasTextModifiers, CanvasDevice device)
        {
            ImageInfo newii = null;
            Rect symbolBounds = ShapeUtilities.clone(ii.getSymbolBounds());
            Rect imageBounds = ShapeUtilities.clone(ii.getCanvasRenderTarget().GetBounds(device));
            Point centerPoint = ShapeUtilities.clone(ii.getAnchorPoint());
            TextInfo tiEchelon = null;
            TextInfo tiAM = null;
            Rect echelonBounds = Rect.Empty;
            Rect amBounds = Rect.Empty;
            Color textColor = Colors.Black;
            Color textBackgroundColor = Colors.Transparent;
            int buffer = 0;
            //ctx = null;
            int offsetX = 0;
            int offsetY = 0;
            int symStd = RS.getSymbologyStandard();
            CanvasTextFormat font = RS.getLabelFont();
            /*Pen mobilityPen = new Pen(Colors.Black, 2f);
            mobilityPen.MiterLimit = 2;//*/

            try
            {
                if(device == null)
                {
                    device = CanvasDevice.GetSharedDevice();
                }

                if (attributes.ContainsKey(MilStdAttributes.SymbologyStandard))
                {
                    symStd = Convert.ToInt16(attributes[MilStdAttributes.SymbologyStandard]);
                }
                if (attributes.ContainsKey(MilStdAttributes.TextColor))
                {
                    textColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.TextColor]);
                }
                if (attributes.ContainsKey(MilStdAttributes.TextBackgroundColor))
                {
                    textBackgroundColor = SymbolUtilities.getColorFromHexString(attributes[MilStdAttributes.TextBackgroundColor]);
                }

                #region Build Mobility Modifiers

                Rect mobilityBounds = Rect.Empty;

                List<CanvasGeometry> shapes = new List<CanvasGeometry>();
                CanvasPathBuilder mobilityPath = null;
                CanvasPathBuilder mobilityPathFill = null;
                CanvasGeometry cgMobilityPath = null;
                CanvasGeometry cgMobilityPathFill = null;
                if (symbolID[10] == ('M') || symbolID[10] == ('N'))
                {

                    //Draw Mobility
                    int fifth = (int)((symbolBounds.Width * 0.2) + 0.5f);
                    mobilityPath = new CanvasPathBuilder(device);
                    int x = 0;
                    int y = 0;
                    int centerX = 0;
                    int bottomY = 0;
                    int height = 0;
                    int width = 0;
                    int middleY = 0;
                    int wheelOffset = 2;
                    int wheelSize = fifth;//10;
                    int rrHeight = fifth;//10;
                    int rrArcWidth = (int)((fifth * 1.5) + 0.5f);//16;

                    String mobility = symbolID.Substring(10, 2);
                    x = (int)symbolBounds.Left;
                    y = (int)symbolBounds.Top;
                    height = (int)(symbolBounds.Height);
                    width = (int)(symbolBounds.Width);
                    bottomY = y + height + 2;

                    if (symbolID[10] == ('M'))
                    {
                        bottomY = y + height + 2;

                        //wheelSize = width / 7;
                        //rrHeight = width / 7;
                        //rrArcWidth = width / 7;
                        if (mobility.Equals("MO"))
                        {
                            //line
                            mobilityPath.BeginFigure(x, bottomY);
                            mobilityPath.AddLine(x + width, bottomY);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(x, bottomY, x + width, bottomY);

                            //left circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device,new Vector2(x, bottomY + wheelOffset),wheelSize,wheelSize));
                            //mobilityPath.AddEllipse(x, bottomY + wheelOffset, wheelSize, wheelSize);


                            //right circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new System.Numerics.Vector2(x + width - wheelSize, bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + width - wheelSize, bottomY + wheelOffset, wheelSize, wheelSize);

                        }
                        else if (mobility.Equals("MP"))
                        {
                            //line
                            mobilityPath.BeginFigure(x, bottomY);
                            mobilityPath.AddLine(x + width, bottomY);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //PathUtilties.AddLine(mobilityPath, x, bottomY, x + width, bottomY);

                            //left circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x, bottomY + wheelOffset), wheelSize, wheelSize));

                            //right circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x + width - wheelSize, bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + width - wheelSize, bottomY + wheelOffset, wheelSize, wheelSize);

                            //center wheel
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x + (width / 2) - (wheelSize / 2), bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + (width / 2) - (wheelSize / 2), bottomY + wheelOffset, wheelSize, wheelSize);
                            
                        }
                        else if (mobility.Equals("MQ"))
                        {
                            //round Rect
                            mobilityPath.AddGeometry(CanvasGeometry.CreateRoundedRectangle(device, x, bottomY, width, rrHeight, rrHeight / 2, rrHeight / 2));
                            //mobilityPath.AddPath(ShapeUtilities.createRoundedRect(new Rect(x, bottomY, width, rrHeight), rrHeight / 2), false);

                        }
                        else if (mobility.Equals("MR"))
                        {
                            //round Rect
                            mobilityPath.AddGeometry(CanvasGeometry.CreateRoundedRectangle(device, x, bottomY, width, rrHeight, rrHeight / 2, rrHeight / 2));
                            //mobilityPath.AddPath(ShapeUtilities.createRoundedRect(new Rect(x, bottomY, width, rrHeight), wheelSize / 2), false);

                            //left circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x - wheelSize - wheelSize, bottomY), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x - wheelSize - wheelSize, bottomY, wheelSize, wheelSize);
                            
                        }
                        else if (mobility.Equals("MS"))
                        {
                            //line
                            mobilityPath.BeginFigure(x + wheelSize, bottomY + (wheelSize / 2));
                            mobilityPath.AddLine(x + width - wheelSize, bottomY + (wheelSize / 2));
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            /*mobilityPath.AddLine(x + wheelSize, bottomY + (wheelSize / 2),
                                    x + width - wheelSize, bottomY + (wheelSize / 2));//*/


                            //left circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x, bottomY), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x, bottomY, wheelSize, wheelSize);

                            //right circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x + width - wheelSize, bottomY), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + width - wheelSize, bottomY, wheelSize, wheelSize);

                        }
                        else if (mobility.Equals("MT"))
                        {

                            //line
                            mobilityPath.BeginFigure(x, bottomY);
                            mobilityPath.AddLine(x + width, bottomY);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(x, bottomY, x + width, bottomY);

                            //left circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x + wheelSize, bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + wheelSize, bottomY + wheelOffset, wheelSize, wheelSize);

                            //left circle2
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x, bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x, bottomY + wheelOffset, wheelSize, wheelSize);

                            //right circle
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x + width - wheelSize, bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + width - wheelSize, bottomY + wheelOffset, wheelSize, wheelSize);

                            //right circle2
                            mobilityPath.AddGeometry(CanvasGeometry.CreateEllipse(device, new Vector2(x + width - wheelSize - wheelSize, bottomY + wheelOffset), wheelSize, wheelSize));
                            //mobilityPath.AddEllipse(x + width - wheelSize - wheelSize, bottomY + wheelOffset, wheelSize, wheelSize);

                        }
                        else if (mobility.Equals("MU"))
                        {
                            float halfWidth = (rrArcWidth * 0.5f);
                            mobilityPath.BeginFigure(x, bottomY);
                            mobilityPath.AddLine(x + halfWidth, bottomY + halfWidth);
                            mobilityPath.AddLine(x + width, bottomY + halfWidth);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                           /* mobilityPath.AddLine(x, bottomY, x + halfWidth, bottomY + halfWidth);
                            mobilityPath.AddLine(x + halfWidth, bottomY + halfWidth, x + width, bottomY + halfWidth);//*/
                        }
                        else if (mobility.Equals("MV"))
                        {
                            mobilityPath.BeginFigure(x, bottomY);
                            mobilityPath.AddCubicBezier(new Vector2(x, bottomY), new Vector2(x - rrHeight, bottomY + rrHeight / 2), new Vector2(x, bottomY + rrHeight));
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddBezier(x, bottomY, x, bottomY, x - rrHeight, bottomY + rrHeight / 2, x, bottomY + rrHeight);

                            mobilityPath.BeginFigure(x, bottomY + rrHeight);
                            mobilityPath.AddLine(x + width, bottomY + rrHeight);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(x, bottomY + rrHeight, x + width, bottomY + rrHeight);


                            mobilityPath.BeginFigure(x + width, bottomY + rrHeight);
                            mobilityPath.AddCubicBezier(new Vector2(x + width, bottomY + rrHeight), new Vector2(x + width + rrHeight, bottomY + rrHeight / 2), new Vector2(x + width, bottomY));
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddBezier(x + width, bottomY + rrHeight, x + width, bottomY + rrHeight, x + width + rrHeight, bottomY + rrHeight / 2, x + width, bottomY);

                        }
                        else if (mobility.Equals("MW"))
                        {
                            centerX = (int)((symbolBounds.X + (symbolBounds.Width / 2)) + 0.5);
                            int angleWidth = rrHeight / 2;

                            mobilityPath.BeginFigure(centerX, bottomY + rrHeight + 2);
                            mobilityPath.AddLine(centerX - angleWidth, bottomY);
                            mobilityPath.AddLine(centerX - angleWidth * 2, bottomY + rrHeight + 2);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(centerX, bottomY + rrHeight + 2, centerX - angleWidth, bottomY);
                            //mobilityPath.AddLine(centerX - angleWidth, bottomY, centerX - angleWidth * 2, bottomY + rrHeight + 2);

                            mobilityPath.BeginFigure(centerX, bottomY + rrHeight + 2);
                            mobilityPath.AddLine(centerX + angleWidth, bottomY);
                            mobilityPath.AddLine(centerX + angleWidth * 2, bottomY + rrHeight + 2);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.StartFigure();
                            //mobilityPath.AddLine(centerX, bottomY + rrHeight + 2, centerX + angleWidth, bottomY);
                            //mobilityPath.AddLine(centerX + angleWidth, bottomY, centerX + angleWidth * 2, bottomY + rrHeight + 2);

                        }
                        else if (mobility.Equals("MX"))
                        {
                            centerX = (int)((symbolBounds.X + (symbolBounds.Width / 2)) + 0.5);

                            mobilityPath.BeginFigure(x + width, bottomY);
                            mobilityPath.AddLine(x, bottomY);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(x + width, bottomY, x, bottomY);


                            float quarterX = (centerX - x) / 2;
                            ////var quarterY = (((bottomY + rrHeight) - bottomY)/2);

                            mobilityPath.BeginFigure(x, bottomY);
                            mobilityPath.AddCubicBezier(new Vector2(x + quarterX, bottomY + rrHeight), new Vector2(centerX + quarterX, bottomY + rrHeight), new Vector2(x + width, bottomY));
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddBezier(x, bottomY, x + quarterX, bottomY + rrHeight, centerX + quarterX, bottomY + rrHeight, x + width, bottomY);

                        }

                        else if (mobility.Equals("MY"))
                        {
                            float incrementX = width / 7f;

                            x = (int)Math.Floor(symbolBounds.X);
                            float r = incrementX;

                            //mobilityPath.arcTo(oval, sAngle, sAngle, moveTo);
                            mobilityPath.AddArc(new Vector2(x, bottomY), r, r, 180, 180);
                            mobilityPath.AddArc(new Vector2(x + incrementX, bottomY), r, r, 180, -180);
                            mobilityPath.AddArc(new Vector2(x + incrementX * 2, bottomY), r, r, 180, 180);
                            mobilityPath.AddArc(new Vector2(x + incrementX * 3, bottomY), r, r, 180, -180);
                            mobilityPath.AddArc(new Vector2(x + incrementX * 4, bottomY), r, r, 180, 180);
                            mobilityPath.AddArc(new Vector2(x + incrementX * 5, bottomY), r, r, 180, -180);
                            mobilityPath.AddArc(new Vector2(x + incrementX * 6, bottomY), r, r, 180, 180);

                        }

                    }
                    //Draw Towed Array Sonar
                    else if (symbolID[10] == ('N'))
                    {

                        int boxHeight = (int)((rrHeight * 0.8f) + 0.5f);
                        bottomY = y + height + (boxHeight / 7);
                        mobilityPathFill = new CanvasPathBuilder(device);
                        offsetY = ShapeUtilities.round(boxHeight / 6);//1;
                        centerX = (int)((symbolBounds.X + (symbolBounds.Width / 2)) + 0.5);
                        int squareOffset = (int)((boxHeight * 0.5f) + 0.5);
                        middleY = ((boxHeight / 2) + bottomY) + offsetY;//+1 for offset from symbol
                        if (symbolID.Substring(10, 2).Equals("NS"))
                        {
                            //subtract 0.5 becase lines 1 pixel thick get aliased into
                            //a line two pixels wide.
                            //line
                            mobilityPath.BeginFigure(centerX - 1, bottomY - 1);
                            mobilityPath.AddLine(centerX - 1, bottomY + boxHeight + offsetY + 2);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(centerX - 1, bottomY - 1, centerX - 1, bottomY + boxHeight + offsetY + 2);


                            //line
                            mobilityPath.BeginFigure(x, middleY);
                            mobilityPath.AddLine(x + width, middleY);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.StartFigure();
                            //mobilityPath.AddLine(x, middleY, x + width, middleY);


                            //square
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, x - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(x - squareOffset, bottomY + offsetY, boxHeight, boxHeight));


                            //square
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, centerX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(centerX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));

                            //square
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, x + width - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(x + width - squareOffset, bottomY + offsetY, boxHeight, boxHeight));

                        }
                        else if (symbolID.Substring(10, 2).Equals("NL"))
                        {
                            int leftX = x + (centerX - x) / 2,
                                    rightX = centerX + (x + width - centerX) / 2;

                            //line vertical left
                            mobilityPath.BeginFigure(leftX, bottomY - 1);
                            mobilityPath.AddLine(leftX, bottomY + offsetY + boxHeight + offsetY + 2);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.AddLine(leftX, bottomY - 1, leftX, bottomY + offsetY + boxHeight + offsetY + 2);


                            //line vertical right
                            mobilityPath.BeginFigure(rightX, bottomY - 1);
                            mobilityPath.AddLine(rightX, bottomY + offsetY + boxHeight + offsetY + 2);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.StartFigure();
                            //mobilityPath.AddLine(rightX, bottomY - 1, rightX, bottomY + offsetY + boxHeight + offsetY + 2);


                            //line horizontal
                            mobilityPath.BeginFigure(x, middleY);
                            mobilityPath.AddLine(x + width, middleY);
                            mobilityPath.EndFigure(CanvasFigureLoop.Open);
                            //mobilityPath.StartFigure();
                            //mobilityPath.AddLine(x, middleY, x + width, middleY);
                            

                            //square left
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, x - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(x - squareOffset, bottomY + offsetY, boxHeight, boxHeight));

                            //square middle
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, centerX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(centerX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));

                            //square right
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, x + width - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(x + width - squareOffset, bottomY + offsetY, boxHeight, boxHeight));

                            //square middle left
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, leftX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(leftX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));

                            //square middle right
                            mobilityPathFill.AddGeometry(CanvasGeometry.CreateRectangle(device, rightX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));
                            //mobilityPathFill.AddRect(new Rect(rightX - squareOffset, bottomY + offsetY, boxHeight, boxHeight));


                        }
                    }

                    //get mobility bounds
                    if (mobilityPath != null)
                    {

                        //build mobility bounds
                        cgMobilityPath = CanvasGeometry.CreatePath(mobilityPath);
                        mobilityBounds = cgMobilityPath.ComputeBounds();


                        Rect mobilityFillBounds = new Rect();
                        if (mobilityPathFill != null)
                        {
                            cgMobilityPathFill = CanvasGeometry.CreatePath(mobilityPathFill);
                            mobilityFillBounds = cgMobilityPathFill.ComputeBounds();
                        }

                        //grow because we use a line thickness of 2.
                        mobilityBounds = new Rect(mobilityBounds.X - 1, mobilityBounds.Y - 1, mobilityBounds.Width+2, mobilityBounds.Height+2);
                        //mobilityBounds.Inflate(1f, 1f);
                        imageBounds = ShapeUtilities.union(imageBounds, mobilityBounds);
                    }
                }

                #endregion

                #region Build Echelon
                //Draw Echelon
                String strEchelon = SymbolUtilities.getEchelon(symbolID);//symbolID.substring(11, 12);
                if (strEchelon != null)
                {
                    strEchelon = SymbolUtilities.getEchelonText(strEchelon);
                }
                if (strEchelon != null && SymbolUtilities.hasInstallationModifier(symbolID) == false
                        && SymbolUtilities.canUnitHaveModifier(symbolID, ModifiersUnits.B_ECHELON))
                {

                    if (strEchelon != null)
                    {
                        int outlineOffset = RS.getTextOutlineWidth();

                        //tiEchelon = new TextInfo(strEchelon, 0, 0, font, _g);
                        tiEchelon = new TextInfo(device, strEchelon);
                        
                        echelonBounds = tiEchelon.getTextBounds();

                        int y = (int)Math.Round(symbolBounds.Top - echelonBounds.Height);
                        int x = (int)Math.Round(symbolBounds.Left + (symbolBounds.Width / 2) - (echelonBounds.Width / 2));
                        tiEchelon.setLocation(x, y);
                        echelonBounds = tiEchelon.getTextBounds();

                        //There will never be lowercase characters in an echelon so trim that fat.    
                        //Remove the descent from the bounding box.
                        //tiEchelon.getTextOutlineBounds();//.shiftBR(0,ShapeUtilities.round(-(echelonBounds.Height*0.3)));                         

                        //make echelon bounds a little more spacious for things like nearby labels and Task Force.
                        //echelonBounds.Inflate(outlineOffset, outlineOffset);// ShapeUtilities.grow(echelonBounds, outlineOffset);
                        //tiEchelon.getTextOutlineBounds();
                        //                RectUtilities.shift(echelonBounds, x, -outlineOffset);
                        //echelonBounds.shift(0,-outlineOffset);// - ShapeUtilities.round(echelonOffset/2));
                        //tiEchelon.setLocation(x, y - outlineOffset);

                        imageBounds = ShapeUtilities.union(imageBounds, echelonBounds);

                    }
                }
                #endregion

                #region Build Affiliation Modifier
                String affiliationModifier = null;
                if (RS.getDrawAffiliationModifierAsLabel() == false)
                {
                    affiliationModifier = SymbolUtilities.getUnitAffiliationModifier(symbolID, symStd);
                }
                if (affiliationModifier != null)
                {

                    int amOffset = 2;
                    int outlineOffset = RS.getTextOutlineWidth();

                    tiAM = new TextInfo(device,affiliationModifier);
                    amBounds = tiAM.getTextBounds();

                    double x, y;

                    if (echelonBounds != Rect.Empty
                            && ((echelonBounds.Left + echelonBounds.Width > symbolBounds.Left + symbolBounds.Width)))
                    {
                        y = (symbolBounds.Top - amOffset);
                        x = echelonBounds.Left + echelonBounds.Width;
                    }
                    else
                    {
                        y = (symbolBounds.Top - amOffset);
                        x = (symbolBounds.Left + symbolBounds.Width);
                    }
                    tiAM.setLocation(x, y);

                    //adjust for outline.
                    amBounds = tiAM.getTextBoundsWithOutline();
                    tiAM.shift(-outlineOffset, -outlineOffset);

                    imageBounds = ShapeUtilities.union(imageBounds, amBounds);
                }
                #endregion

                #region Build Task Force
                Rect tfBounds = Rect.Empty;
                Rect tfRect = Rect.Empty;
                if (SymbolUtilities.isTaskForce(symbolID))
                {
                    if (echelonBounds != Rect.Empty)
                    {
                        tfRect = new Rect(echelonBounds.X, echelonBounds.Y, echelonBounds.Width, symbolBounds.Y - echelonBounds.Y);
                        tfBounds = ShapeUtilities.clone(tfRect);
                    }
                    else
                    {
                        double height = (symbolBounds.Height / 4);
                        double width = (symbolBounds.Width / 3);

                        tfRect = new Rect(symbolBounds.Left + width,
                                symbolBounds.Top - height,
                                width,
                                height);

                        tfBounds = new Rect(tfRect.Left + -1,
                                tfRect.Top - 1,
                                tfRect.Width + 2,
                                tfRect.Height + 2);

                    }
                    imageBounds = ShapeUtilities.union(imageBounds, tfBounds);
                }
                #endregion

                #region Build Feint Dummy Indicator
                Rect fdiBounds = Rect.Empty;
                Point fdiTop = new Point();// Point.Empty;
                Point fdiLeft = new Point();
                Point fdiRight = new Point();

                if (SymbolUtilities.isFeintDummy(symbolID)
                        || SymbolUtilities.isFeintDummyInstallation(symbolID))
                {
                    //create feint indicator /\
                    fdiLeft = new Point(symbolBounds.Left, symbolBounds.Top);
                    fdiRight = new Point((symbolBounds.Left + symbolBounds.Width), symbolBounds.Top);

                    char affiliation = symbolID[1];
                    if (affiliation == ('F')
                            || affiliation == ('A')
                            || affiliation == ('D')
                            || affiliation == ('M')
                            || affiliation == ('J')
                            || affiliation == ('K'))
                    {
                        fdiTop = new Point((ShapeUtilities.getCenterX(symbolBounds)), ShapeUtilities.round(symbolBounds.Top - (symbolBounds.Height * .75f)));
                    }
                    else
                    {
                        fdiTop = new Point((ShapeUtilities.getCenterX(symbolBounds)), ShapeUtilities.round(symbolBounds.Top - (symbolBounds.Height * .54f)));
                    }

                    fdiBounds = new Rect(fdiLeft.X, fdiLeft.Y, 1, 1);
                    fdiBounds = ShapeUtilities.union(fdiBounds, fdiTop);
                    fdiBounds = ShapeUtilities.union(fdiBounds, fdiRight);

                    if (echelonBounds != null)
                    {
                        double shiftY = (symbolBounds.Top - echelonBounds.Height - 2);
                        fdiLeft.Y = fdiLeft.Y + shiftY;
                        fdiTop.Y = fdiLeft.Y + shiftY;
                        fdiRight.Y = fdiLeft.Y + shiftY;
                        fdiBounds.Y = fdiLeft.Y + shiftY;
                        /*(fdiLeft.Offset(0, shiftY);
                        fdiTop.Offset(0, shiftY);
                        fdiRight.Offset(0, shiftY);
                        fdiBounds.Offset(0, shiftY);//*/
                    }

                    imageBounds = ShapeUtilities.union(imageBounds, fdiBounds);

                }
                #endregion

                #region Build Installation
                Rect instRect = Rect.Empty;
                Rect instBounds = Rect.Empty;
                if (SymbolUtilities.hasInstallationModifier(symbolID))
                {//the actual installation symbols have the modifier
                    //built in.  everything else, we have to draw it.
                    //
                    ////get indicator dimensions////////////////////////////////
                    int width;
                    int height;
                    char affiliation = SymbolUtilities.getAffiliation(symbolID);

                    if (affiliation == 'F'
                            || affiliation == 'A'
                            || affiliation == 'D'
                            || affiliation == 'M'
                            || affiliation == 'J'
                            || affiliation == 'K')
                    {
                        //4th height, 3rd width
                        height = ShapeUtilities.round(symbolBounds.Height / 4);
                        width = ShapeUtilities.round(symbolBounds.Width / 3);
                    }
                    else if (affiliation == 'H' || affiliation == 'S')//hostile,suspect
                    {
                        //6th height, 3rd width
                        height = ShapeUtilities.round(symbolBounds.Height / 6);
                        width = ShapeUtilities.round(symbolBounds.Width / 3);
                    }
                    else if (affiliation == 'N' || affiliation == 'L')//neutral,exercise neutral
                    {
                        //6th height, 3rd width
                        height = ShapeUtilities.round(symbolBounds.Height / 6);
                        width = ShapeUtilities.round(symbolBounds.Width / 3);
                    }
                    else if (affiliation == 'P'
                            || affiliation == 'U'
                            || affiliation == 'G'
                            || affiliation == 'W')
                    {
                        //6th height, 3rd width
                        height = ShapeUtilities.round(symbolBounds.Height / 6);
                        width = ShapeUtilities.round(symbolBounds.Width / 3);
                    }
                    else
                    {
                        //6th height, 3rd width
                        height = ShapeUtilities.round(symbolBounds.Height / 6);
                        width = ShapeUtilities.round(symbolBounds.Width / 3);
                    }

                    //                    if(width * 3 < symbolBounds.Width)
                    //                        width++;
                    //set installation position/////////////////////////////////
                    //set position of indicator
                    if (affiliation == 'F'
                            || affiliation == 'A'
                            || affiliation == 'D'
                            || affiliation == 'M'
                            || affiliation == 'J'
                            || affiliation == 'K'
                            || affiliation == 'N'
                            || affiliation == 'L')
                    {
                        instRect = new Rect((int)(symbolBounds.Left + width),
                                (int)(symbolBounds.Top - height),
                                width,
                                height);
                    }
                    else if (affiliation == 'H' || affiliation == 'S')//hostile,suspect
                    {
                        instRect = new Rect((int)symbolBounds.Left + width,
                                ShapeUtilities.round(symbolBounds.Top - (height * 0.15f)),
                                width,
                                height);
                    }
                    else if (affiliation == 'P'
                            || affiliation == 'U'
                            || affiliation == 'G'
                            || affiliation == 'W')
                    {
                        instRect = new Rect((int)symbolBounds.Left + width,
                                ShapeUtilities.round(symbolBounds.Top - (height * 0.3f)),
                                width,
                                height);
                    }
                    else
                    {
                        instRect = new Rect((int)symbolBounds.Left + width,
                                ShapeUtilities.round(symbolBounds.Top - (height * 0.3f)),
                                width,
                                height);
                    }

                    /*instRect = new SO.Rect(symbolBounds.Left + width,
                     symbolBounds.Top - height,
                     width,
                     height);//*/
                    //generate installation bounds//////////////////////////////
                    instBounds = new Rect(instRect.Left + -1,
                            instRect.Top - 1,
                            instRect.Width + 2,
                            instRect.Height + 2);

                    imageBounds = ShapeUtilities.union(imageBounds, instBounds);

                }
                #endregion

                #region Build HQ Staff
                Point pt1HQ = new Point();
                Point pt2HQ = new Point();
                Rect hqBounds = Rect.Empty;
                //Draw HQ Staff
                if (SymbolUtilities.isHQ(symbolID))
                {

                    char affiliation = symbolID[1];
                    //get points for the HQ staff
                    if (affiliation == ('F')
                            || affiliation == ('A')
                            || affiliation == ('D')
                            || affiliation == ('M')
                            || affiliation == ('J')
                            || affiliation == ('K')
                            || affiliation == ('N')
                            || affiliation == ('L'))
                    {
                        pt1HQ = new Point((int)symbolBounds.Left + 1,
                                (int)(symbolBounds.Top + symbolBounds.Height - 1));
                        pt2HQ = new Point((int)pt1HQ.X, (int)(pt1HQ.Y + symbolBounds.Height));
                    }
                    else
                    {
                        pt1HQ = new Point((int)symbolBounds.Left + 1,
                                (int)(symbolBounds.Top + (symbolBounds.Height / 2)));
                        pt2HQ = new Point((int)pt1HQ.X, (int)(pt1HQ.Y + symbolBounds.Height));
                    }

                    //create bounding Rect for HQ staff.
                    hqBounds = new Rect(pt1HQ.X, pt1HQ.Y, 2, pt2HQ.Y - pt1HQ.Y);
                    //adjust the image bounds accordingly.
                    imageBounds.Height = imageBounds.Height + (pt2HQ.Y - imageBounds.Bottom);
                    imageBounds = ShapeUtilities.union(imageBounds, hqBounds);
                    //adjust symbol center
                    centerPoint.X = pt2HQ.X;
                    centerPoint.Y = pt2HQ.Y;
                }
                #endregion

                #region Build DOM Arrow
                Point[] domPoints = null;
                Rect domBounds = Rect.Empty;
                if (modifiers != null && modifiers.ContainsKey(ModifiersUnits.Q_DIRECTION_OF_MOVEMENT))
                {
                    String strQ = modifiers[ModifiersUnits.Q_DIRECTION_OF_MOVEMENT];

                    if (strQ != null && SymbolUtilities.isNumber(strQ))
                    {
                        float q = (float)Convert.ToDouble(strQ);

                        Boolean isY = (modifiers.ContainsKey(ModifiersUnits.Y_LOCATION));

                        TextInfo tiY = new TextInfo(device, "Y");

                        domPoints = createDOMArrowPoints(symbolID, symbolBounds, centerPoint, q, tiY.getTextBounds().Height);

                        domBounds = new Rect(domPoints[0].X, domPoints[0].Y, 1, 1);

                        Point temp = new Point();
                        for (int i = 1; i < 6; i++)
                        {
                            temp = domPoints[i];
                            if (temp.X != 0 && temp.Y != 0)
                            {
                                domBounds = ShapeUtilities.union(domBounds, temp);
                            }
                        }
                        domBounds = ShapeUtilities.inflate(domBounds,1, 1);
                        imageBounds = ShapeUtilities.union(imageBounds, domBounds);
                    }
                }
                #endregion

                #region Build Operational Condition Indicator
                Rect ociBounds = Rect.Empty;
                int ociOffset = 4;
                if (mobilityBounds != Rect.Empty)
                {
                    ociOffset = ShapeUtilities.round(mobilityBounds.Height);
                }
                Rect ociShape = processOperationalConditionIndicator(symbolID, symbolBounds, ociOffset);
                if (ociShape != Rect.Empty)
                {
                    Rect temp = ShapeUtilities.clone(ociShape);
                    temp = ShapeUtilities.inflate(temp,2, 3);
                    ociBounds = temp;
                    imageBounds = ShapeUtilities.union(imageBounds, ociBounds);
                }
                #endregion

                #region Shift Modifiers
                if (imageBounds.Left < 0 || imageBounds.Top < 0)
                {
                    double shiftX = Math.Abs(imageBounds.Left);
                    double shiftY = Math.Abs(imageBounds.Top);

                    if (hqBounds != Rect.Empty)
                    {
                        pt1HQ = ShapeUtilities.offset(pt1HQ,shiftX, shiftY);
                        pt2HQ = ShapeUtilities.offset(pt2HQ, shiftX, shiftY);
                    }
                    if (echelonBounds != Rect.Empty)
                    {
                        tiEchelon.setLocation(tiEchelon.getLocation().X + shiftX, tiEchelon.getLocation().Y + shiftY);
                    }
                    if (amBounds != Rect.Empty)
                    {
                        tiAM.setLocation(tiAM.getLocation().X + shiftX, tiAM.getLocation().Y + shiftY);
                    }
                    if (tfBounds != Rect.Empty)
                    {
                        tfRect = ShapeUtilities.offset(tfRect, shiftX, shiftY);
                        tfBounds = ShapeUtilities.offset(tfBounds,shiftX, shiftY);
                    }
                    if (instBounds != Rect.Empty)
                    {
                        instRect = ShapeUtilities.offset(instRect,shiftX, shiftY);
                        instBounds = ShapeUtilities.offset(instBounds,shiftX, shiftY);
                    }
                    if (fdiBounds != Rect.Empty)
                    {
                        fdiBounds = ShapeUtilities.offset(fdiBounds,shiftX, shiftY);
                        fdiLeft = ShapeUtilities.offset(fdiLeft, shiftX, shiftY);
                        fdiTop = ShapeUtilities.offset(fdiTop, shiftX, shiftY);
                        fdiRight = ShapeUtilities.offset(fdiRight,shiftX, shiftY);
                    }
                    if (ociBounds != Rect.Empty)
                    {
                        ociBounds = ShapeUtilities.offset(ociBounds,shiftX, shiftY);
                        ociShape = ShapeUtilities.offset(ociShape,shiftX, shiftY);
                    }
                    if (domBounds != Rect.Empty)
                    {
                        for (int i = 0; i < 6; i++)
                        {
                            Point temp = domPoints[i];

                            if (temp.X != 0 && temp.Y != 0)
                                temp = ShapeUtilities.offset(temp,shiftX, shiftY);

                            domPoints[i] = temp;

                        }
                        domBounds = ShapeUtilities.offset(domBounds,shiftX, shiftY);
                    }
                    if (mobilityBounds != Rect.Empty)
                    {
                        Matrix3x2 translation = Matrix3x2.CreateTranslation((float)shiftX, (float)shiftY);

                        //shift mobility points
                        cgMobilityPath.Transform(translation);
                        if(cgMobilityPathFill != null)
                        {
                            cgMobilityPathFill.Transform(translation);
                        }

                        mobilityBounds = ShapeUtilities.offset(mobilityBounds,shiftX, shiftY);
                    }

                    centerPoint = ShapeUtilities.offset(centerPoint,shiftX, shiftY);
                    symbolBounds = ShapeUtilities.offset(symbolBounds, shiftX, shiftY);
                    imageBounds = ShapeUtilities.offset(imageBounds, shiftX, shiftY);
                }
                #endregion

                #region Draw Modifiers
                CanvasRenderTarget bmp = new CanvasRenderTarget(device, (float)imageBounds.Width, (float)imageBounds.Height, 96);
                //Bitmap bmp = new Bitmap(imageBounds.Width, imageBounds.Height);
                //Graphics g = Graphics.FromImage(bmp);


                //render////////////////////////////////////////////////////////
                using (CanvasDrawingSession ds = bmp.CreateDrawingSession())
                {
                    ds.Antialiasing = CanvasAntialiasing.Antialiased;
                    ds.TextAntialiasing = CanvasTextAntialiasing.ClearType;
                    //Pen pen = new Pen(Color.Black, 2f);
                    //g.SmoothingMode = SmoothingMode.AntiAlias;
                    if (hqBounds != Rect.Empty)
                    {
                        ds.DrawLine(pt1HQ.ToVector2(), pt2HQ.ToVector2(), Colors.Black, 2f);
                        //g.DrawLine(pen, pt1HQ.X, pt1HQ.Y, pt2HQ.X, pt2HQ.Y);
                    }

                    if (tfBounds != Rect.Empty)
                    {
                        ds.DrawRectangle(tfRect, Colors.Black,2f);
                        //g.DrawRect(pen, tfRect);
                    }

                    if (instBounds != Rect.Empty)
                    {
                        ds.FillRectangle(tfRect,Colors.Black);
                        //g.FillRect(Brushes.Black, instRect);
                    }

                    if (echelonBounds != Rect.Empty)
                    {
                        /*TextInfo[] aTiEchelon =
                        {
                            tiEchelon
                        };
                        renderText(g, aTiEchelon, textColor, textBackgroundColor);//*/
                        tiEchelon.drawText(ds, textColor);
                        echelonBounds = Rect.Empty;
                        tiEchelon = null;
                    }

                    if (amBounds != Rect.Empty)
                    {
                        /*TextInfo[] aTiAM =
                        {
                            tiAM
                        };
                        renderText(g, aTiAM, textColor, textBackgroundColor);//*/
                        tiAM.drawText(ds, textColor);
                        amBounds = Rect.Empty;
                        tiAM = null;
                    }

                    if (fdiBounds != Rect.Empty)
                    {
                        CanvasStrokeStyle style = new CanvasStrokeStyle();
                        
                        if (symbolBounds.Width > 19)
                        {
                            style.CustomDashStyle = new float[] { 6f, 4f };
                        }
                        else
                        {
                            style.CustomDashStyle = new float[] { 5f, 3f };
                        }

                        style.LineJoin = CanvasLineJoin.Miter;
                        style.MiterLimit = 3;
                        
                        //pen.LineJoin = LineJoin.Miter;
                        //pen.MiterLimit = 3;
                        //pen.Width = 2;
                        
                        //GraphicsPath fdiPath = new GraphicsPath();

                        //fdiPath.AddLine(fdiLeft.X, fdiLeft.Y, fdiTop.X, fdiTop.Y);
                        //fdiPath.AddLine(fdiTop.X, fdiTop.Y, fdiRight.X, fdiRight.Y);

                        ds.DrawLine(fdiLeft.ToVector2(), fdiTop.ToVector2(), Colors.Black, 2f);

                        //g.DrawPath(pen, fdiPath);

                        fdiBounds = Rect.Empty;

                    }

                    if (mobilityBounds != Rect.Empty)
                    {


                        //ctx.lineCap = "butt";
                        //ctx.lineJoin = "miter";
                        if (symbolID[10] == ('N'))
                        {
                            ds.Antialiasing = CanvasAntialiasing.Aliased;
                            //mobilityPaint.setAntiAlias(false);
                            //g.SmoothingMode = SmoothingMode.None;
                        }
                        ds.DrawGeometry(cgMobilityPath, Colors.Black, 2f);
                       // g.DrawPath(mobilityPen, mobilityPath);

                        if (cgMobilityPathFill != null)
                        {
                            ds.FillGeometry(cgMobilityPathFill,Colors.Black);
                            //g.FillPath(Brushes.Black, mobilityPathFill);
                        }

                        mobilityBounds = Rect.Empty;

                    }

                    if (ociBounds != Rect.Empty)
                    {
                        Color statusColor = Colors.Black;
                        char status = symbolID[3];
                        if (status == ('C'))//Fully Capable
                        {
                            statusColor = Colors.Green;
                        }
                        else if (status == ('D'))//Damage
                        {
                            statusColor = Colors.Yellow;
                        }
                        else if (status == ('X'))
                        {
                            statusColor = Colors.Red;
                        }
                        else if (status == ('F'))//full to capacity(hospital)
                        {
                            statusColor = Colors.Blue;
                        };

                        ds.FillRectangle(ociBounds, Colors.Black);
                        //g.FillRect(Brushes.Black, ociBounds);
                        ds.FillRectangle(ociShape, statusColor);
                        //g.FillRect(new SolidBrush(statusColor), ociShape);

                        ociBounds = Rect.Empty;
                        ociShape = Rect.Empty;
                    }

                    //draw original icon.        
                    //ctx.drawBitmap(ii.getImage(), null, symbolBounds, null);
                    ds.DrawImage(ii.getCanvasRenderTarget(), (float)symbolBounds.X, (float)symbolBounds.Y);
                    //g.DrawImageUnscaled(ii.getBitmap(), symbolBounds.X, symbolBounds.Y);

                    if (domBounds != Rect.Empty)
                    {
                        drawDOMArrow(device, ds, domPoints);

                        domBounds = Rect.Empty;
                        domPoints = null; ;
                    }

                    #endregion
                }
                
               
                /*GraphicsUnit pixel = GraphicsUnit.Pixel;
                Rect outline = ShapeUtilities.cloneToRect(bmp.GetBounds(ref pixel));
                outline.Width = outline.Width - 1;
                outline.Height = outline.Height - 1;
                g.DrawRect(Pens.Red, outline);//*/

                newii = new ImageInfo(bmp, centerPoint, symbolBounds,bmp.GetBounds(device));

                #region Cleanup
                if (newii != null)
                {
                    return newii;
                }
                else
                {
                    return null;
                }
                #endregion
            }
            catch (Exception exc)
            {
                ErrorLogger.LogException("SinglePointRenderer", "ProcessUnitDisplayModifiers", exc);
                return null;
            }
        }