In the dark ages of .NET 2.0, if you wanted OpenType text, you basically had to write your own OT engine. But in .NET 3.5, you can hijack all of the OT functionality in WPF rich typography, even if you are working with something like ASP.NET server-side image generation. Here’s how.
To begin with, you need to create the typographic elements that you are going to render:
Run r1 = new Run(text.Substring(0, 1))
{
FontFamily = new FontFamily(fontName),
FontSize = fontSize,
FontStyle = FontStyles.Italic
};
if (char.IsLetter(text[0]))
r1.SetValue(Typography.StandardSwashesProperty, 1);
Run r2 = new Run(text.Substring(1))
{
FontFamily = new FontFamily(fontName),
FontSize = fontSize
};
r2.SetValue(Typography.NumeralStyleProperty, FontNumeralStyle.OldStyle);
Paragraph p = new Paragraph {TextAlignment = TextAlignment.Left};
p.Inlines.Add(r1);
p.Inlines.Add(r2);
FlowDocument fd = new FlowDocument(p);
Now there’a challenge: how to render a FlowDocument onto a bitmap? We need to create a viewer and carry out the measure and arrange steps:
FlowDocumentPageViewer fdpv = new FlowDocumentPageViewer {Document = fd};
fdpv.Measure(new Size(800, 200));
fdpv.Arrange(new Rect(0, 0, 800, 200));
The last step is to render the text onto a target bitmap:
RenderTargetBitmap rtb = new RenderTargetBitmap(400, 100, 72, 72, PixelFormats.Pbgra32);
rtb.Render(fdpv);
PngBitmapEncoder enc = new PngBitmapEncoder();
enc.Frames.Add(BitmapFrame.Create(rtb));
using (Stream fs = File.Create(location))
{
enc.Save(fs);
}
Of course, there’s a critical step missing: ClearType. Without it, all our beautiful typography is meaningless.