123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165 |
- #region MIT License
- /*Copyright (c) 2012 Robert Rouhani <robert.rouhani@gmail.com>
- Permission is hereby granted, free of charge, to any person obtaining a copy of
- this software and associated documentation files (the "Software"), to deal in
- the Software without restriction, including without limitation the rights to
- use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
- of the Software, and to permit persons to whom the Software is furnished to do
- so, subject to the following conditions:
- The above copyright notice and this permission notice shall be included in all
- copies or substantial portions of the Software.
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
- SOFTWARE.*/
- #endregion
- using System;
- using System.Drawing;
- using System.Drawing.Imaging;
- using System.IO;
- using System.Runtime.InteropServices;
- using System.Threading;
- using SharpFont;
- namespace Examples
- {
- class Program
- {
- public static void Main(string[] args)
- {
- //TODO make several examples in an example browser
- try
- {
- using (Library lib = new Library())
- {
- Console.WriteLine("FreeType version: " + lib.Version + "\n");
- using (Face face = lib.NewFace(@"Fonts/Cousine-Regular-Latin.ttf", 0))
- {
- //attach a finalizer delegate
- face.Generic = new Generic(IntPtr.Zero, OnFaceDestroyed);
- //write out some basic font information
- Console.WriteLine("Information for font " + face.FamilyName);
- Console.WriteLine("====================================");
- Console.WriteLine("Number of faces: " + face.FaceCount);
- Console.WriteLine("Face flags: " + face.FaceFlags);
- Console.WriteLine("Style: " + face.StyleName);
- Console.WriteLine("Style flags: " + face.StyleFlags);
- face.SetCharSize(0, 32 * 64, 0, 96);
- Console.WriteLine("\nWriting string \"Hello World!\":");
- Bitmap bmp = RenderString(face, "Hello World!");
- bmp.Save("helloworld.png", ImageFormat.Png);
- bmp.Dispose();
- Console.WriteLine("Done!\n");
- }
- }
- }
- catch (FreeTypeException e)
- {
- Console.Write(e.Error.ToString());
- }
- Console.ReadKey();
- }
- public static Bitmap RenderString(Face face, string text)
- {
- int penX = 0, penY = 0;
- int width = 0;
- int height = 0;
- //measure the size of the string before rendering it, requirement of Bitmap.
- for (int i = 0; i < text.Length; i++)
- {
- char c = text[i];
- uint glyphIndex = face.GetCharIndex(c);
- face.LoadGlyph(glyphIndex, LoadFlags.Default, LoadTarget.Normal);
- width += (int)face.Glyph.Advance.X >> 6;
- if (face.HasKerning && i < text.Length - 1)
- {
- char cNext = text[i + 1];
- width += (int)face.GetKerning(glyphIndex, face.GetCharIndex(cNext), KerningMode.Default).X >> 6;
- }
- if (face.Glyph.Metrics.Height >> 6 > height)
- height = (int)face.Glyph.Metrics.Height >> 6;
- }
- //create a new bitmap that fits the string.
- Bitmap bmp = new Bitmap(width, height);
- //draw the string
- for (int i = 0; i < text.Length; i++)
- {
- char c = text[i];
- uint glyphIndex = face.GetCharIndex(c);
- face.LoadGlyph(glyphIndex, LoadFlags.Default, LoadTarget.Normal);
- face.Glyph.RenderGlyph(RenderMode.Normal);
- if (c == ' ')
- {
- penX += (int)face.Glyph.Advance.X >> 6;
- if (face.HasKerning && i < text.Length - 1)
- {
- char cNext = text[i + 1];
- width += (int)face.GetKerning(glyphIndex, face.GetCharIndex(cNext), KerningMode.Default).X >> 6;
- }
- penY += (int)face.Glyph.Advance.Y >> 6;
- continue;
- }
- BitmapData data = bmp.LockBits(new Rectangle(penX, penY + (bmp.Height - face.Glyph.Bitmap.Rows), face.Glyph.Bitmap.Width, face.Glyph.Bitmap.Rows), ImageLockMode.ReadWrite, PixelFormat.Format32bppArgb);
- byte[] pixelAlphas = new byte[face.Glyph.Bitmap.Width * face.Glyph.Bitmap.Rows];
- Marshal.Copy(face.Glyph.Bitmap.Buffer, pixelAlphas, 0, pixelAlphas.Length);
- for (int j = 0; j < pixelAlphas.Length; j++)
- {
- int pixelOffset = (j / data.Width) * data.Stride + (j % data.Width * 4);
- Marshal.WriteByte(data.Scan0, pixelOffset + 3, pixelAlphas[j]);
- }
- bmp.UnlockBits(data);
- penX += (int)face.Glyph.Advance.X >> 6;
- penY += (int)face.Glyph.Advance.Y >> 6;
- if (face.HasKerning && i < text.Length - 1)
- {
- char cNext = text[i + 1];
- width += (int)face.GetKerning(glyphIndex, face.GetCharIndex(cNext), KerningMode.Default).X >> 6;
- }
- }
- return bmp;
- }
- /// <summary>
- /// Called when Face is destroyed.
- /// </summary>
- /// <param name="face">Pointer to the face</param>
- public static void OnFaceDestroyed(IntPtr face)
- {
- //Console.WriteLine(face.FamilyName);
- Console.WriteLine("Face destroyed!");
- }
- }
- }
|