Created by: X  

This xna code snip allows you to draw text, with the option of having that text word wrapped to the specified rectangle or you can specify text alignment info like weather or not the text should be drawn anchored to the bottom right of the rectangle or top right etc.

    public enum TextAlignment

    {

        Top,

        Left,

        Middle,

        Right,

        Bottom,

        TopLeft,

        TopRight,

        BottomLeft,

        BottomRight

    }

 

 

        /// <summary>

        /// Draws a string. 

        /// </summary>

        /// <param name="sb">A reference to a SpriteBatch object that will draw the text.</param>

        /// <param name="fnt">A reference to a SpriteFont object.</param>

        /// <param name="text">The text to be drawn. <remarks>If the text contains \n it

        /// will be treated as a new line marker and the text will drawn acordingy.</remarks></param>

        /// <param name="r">The screen rectangle that the rext should be drawn inside of.</param>

        /// <param name="col">The color of the text that will be drawn.</param>

        /// <param name="align">Specified the alignment within the specified screen rectangle.</param>

        /// <param name="performWordWrap">If true the words within the text will be aranged to rey and

        /// fit within the bounds of the specified screen rectangle.</param>

        /// <param name="offsett">Draws the text at a specified offset relative to the screen

        /// rectangles top left position. </param>

        /// <param name="textBounds">Returns a rectangle representing the size of the bouds of

        /// the text that was drawn.</param>

          public static void DrawString(SpriteBatch sb, SpriteFont fnt, string text, Rectangle r,

          Color col, TextAlignment align, bool performWordWrap, Vector2 offsett, out Rectangle textBounds)

        {

            // check if there is text to draw

            textBounds = r;

            if (text == null) return;

            if (text == string.Empty) return;

 

            StringCollection lines = new StringCollection();

            lines.AddRange(text.Split(new string[] { "\\n"}, StringSplitOptions.RemoveEmptyEntries));

 

            // calc the size of the rect for all the text

            Rectangle tmprect = ProcessLines(fnt, r, performWordWrap, lines);

 

            // setup the position where drawing will start

            Vector2 pos = new Vector2(r.X, r.Y);

            int aStyle = 0;

 

            switch (align)

            {

                case TextAlignment.Bottom:

                    pos.Y = r.Bottom - tmprect.Height;

                    aStyle = 1;

                    break;

                case TextAlignment.BottomLeft:

                    pos.Y = r.Bottom - tmprect.Height;

                    aStyle = 0;

                    break;

                case TextAlignment.BottomRight:

                    pos.Y = r.Bottom - tmprect.Height;

                    aStyle = 2;

                    break;

                case TextAlignment.Left:

                    pos.Y =  r.Y + ((r.Height / 2) - (tmprect.Height / 2));

                    aStyle = 0;

                    break;

                case TextAlignment.Middle:

                    pos.Y =  r.Y + ((r.Height / 2) - (tmprect.Height / 2));

                    aStyle = 1;

                    break;

                case TextAlignment.Right:

                    pos.Y = r.Y + ((r.Height / 2) - (tmprect.Height / 2));

                    aStyle = 2;

                    break;

                case TextAlignment.Top:

                    aStyle = 1;

                    break;

                case TextAlignment.TopLeft:

                    aStyle = 0;

                    break;

                case TextAlignment.TopRight:

                    aStyle = 2;

                    break;

            }

 

            // draw text

            for (int idx = 0; idx < lines.Count; idx++)

            {

                string txt = lines[idx];

                Vector2 size = fnt.MeasureString(txt);

                switch (aStyle)

                {

                    case 0:

                        pos.X = r.X;

                        break;

                    case 1:

                        pos.X = r.X + ((r.Width / 2) - (size.X / 2));

                        break;

                    case 2:

                        pos.X = r.Right - size.X;                      

                        break;

                }

                // draw the line of text

                sb.DrawString(fnt, txt, pos + offsett, col);

                pos.Y += fnt.LineSpacing;

            }

 

            textBounds = tmprect;

        }

 

        internal static Rectangle ProcessLines(SpriteFont fnt, Rectangle r, bool performWordWrap, StringCollection lines)

        {

            // llop through each line in the collection

            Rectangle bounds = r;

            bounds.Width = 0;

            bounds.Height = 0;

            int index = 0;

            float Width = 0;

            bool lineInserted = false;

            while (index < lines.Count)

            {

                // get a line of text

                string linetext = lines[index];

                //measure the line of text

                Vector2 size = fnt.MeasureString(linetext);

 

                // check if the line of text is geater then then the rect we want to draw it inside of

                if (performWordWrap && size.X > r.Width)

                {

                    // find last space character in line

                    string endspace = string.Empty;

                    // deal with trailing spaces

                    if (linetext.EndsWith(" "))

                    {

                        endspace = " ";

                        linetext = linetext.TrimEnd();

                    }

 

                    // get the index of the last space character

                    int i = linetext.LastIndexOf(" ");

                    if (i != -1)

                    {

                        // if there was a space grab the last word in the line

                        string lastword = linetext.Substring(i + 1);

                        // move word to next line

                        if (index == lines.Count - 1)

                        {

                            lines.Add(lastword);

                            lineInserted = true;

                        }

                        else

                        {

                            // prepend last word to begining of next line

                            if (lineInserted)

                            {

                                lines[index + 1] = lastword + endspace + lines[index + 1];

                            }

                            else

                            {

                                lines.Insert(index + 1, lastword);

                                lineInserted = true;

                            }

                        }

 

                        // crop last word from the line that is being processed

                        lines[index] = linetext.Substring(0, i + 1);

 

                    }

                    else

                    {

                        // there appear to be no space characters on this line s move to the next line

                        lineInserted = false;

                        size = fnt.MeasureString(lines[index]);

                        if (size.X > bounds.Width) Width = size.X;

                        bounds.Height += fnt.LineSpacing;// size.Y - 1;

                        index++;

                    }

                }

                else

                {

                    // this line will fit so we can skip to the next line

                    lineInserted = false;

                    size = fnt.MeasureString(lines[index]);

                    if (size.X > bounds.Width) bounds.Width = (int)size.X;

                    bounds.Height += fnt.LineSpacing;//size.Y - 1;

                    index++;

                }

            }

 

            // returns the size of the text

            return bounds;

        }

Creative Commons License
This work is licensed under a Creative Commons Attribution-Noncommercial-Share Alike 2.5 Canada License.

Contact    Resume
Who is Created by: X?