Browse Source

Added more examples for documentation

Marcin Ziąbek 10 months ago
parent
commit
21d9d431af

BIN
Source/QuestPDF.DocumentationExamples/NotoEmoji-Regular.ttf


BIN
Source/QuestPDF.DocumentationExamples/NotoSansArabic-Regular.ttf


+ 18 - 0
Source/QuestPDF.DocumentationExamples/QuestPDF.DocumentationExamples.csproj

@@ -25,4 +25,22 @@
       <ProjectReference Include="..\QuestPDF\QuestPDF.csproj" />
     </ItemGroup>
 
+    <ItemGroup>
+      <None Update="NotoEmoji-Regular.ttf">
+        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
+      </None>
+      <None Update="NotoSansArabic-Regular.ttf">
+        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
+      </None>
+      <None Update="mail-synchronize-icon.svg">
+        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
+      </None>
+      <None Update="unit-test-completed-icon.png">
+        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
+      </None>
+      <None Update="unit-test-failed-icon.png">
+        <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
+      </None>
+    </ItemGroup>
+
 </Project>

+ 154 - 0
Source/QuestPDF.DocumentationExamples/Text/ParagraphStyleExamples.cs

@@ -0,0 +1,154 @@
+using QuestPDF.Fluent;
+using QuestPDF.Helpers;
+using QuestPDF.Infrastructure;
+
+namespace QuestPDF.DocumentationExamples.Text;
+
+public class ParagraphStyleExamples
+{
+    [Test]
+    public void TextAlignment()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(400, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(20);
+                            
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("This is an example of left-aligned text, showcasing how the text starts from the left margin and continues naturally across the container.")
+                                .AlignLeft();
+
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("This text is centered within its container, creating a balanced look, especially for titles or headers.")
+                                .AlignCenter();
+
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("This example demonstrates right-aligned text, often used for dates, numbers, or aligning text to the right margin.")
+                                .AlignRight();
+
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("Justified text adjusts the spacing between words so that both the left and right edges of the text block are aligned, creating a clean, newspaper-like look.")
+                                .Justify();
+    
+                            static IContainer CellStyle(IContainer container) 
+                                => container.Background(Colors.Grey.Lighten3).Padding(10);
+                        });
+
+                });
+            })
+            .GenerateImages(x => "text-paragraph-alignment.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void FirstLineIndentation()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1200));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(Placeholders.Paragraphs())
+                        .ParagraphFirstLineIndentation(40);
+                });
+            })
+            .GenerateImages(x => "text-paragraph-first-line-indentation.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.High, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void Spacing()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1200));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(Placeholders.Paragraphs())
+                        .ParagraphSpacing(10);
+                });
+            })
+            .GenerateImages(x => "text-paragraph-spacing.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.High, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void ClampLines()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(600, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+                    
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(10);
+
+                            var paragraph = Placeholders.Paragraph();
+
+                            column.Item()
+                                .Background(Colors.Grey.Lighten3)
+                                .Padding(5)
+                                .Text(paragraph);
+                            
+                            column.Item()
+                                .Background(Colors.Grey.Lighten3)
+                                .Padding(5)
+                                .Text(paragraph)
+                                .ClampLines(3);
+                        });
+                });
+            })
+            .GenerateImages(x => "text-paragraph-clamp-lines.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void ClampLinesWithCustomEllipsis()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(600, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(Placeholders.Paragraph())
+                        .ClampLines(3, " [...]");
+                });
+            })
+            .GenerateImages(x => "text-paragraph-clamp-lines-custom-ellipsis.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+}

+ 268 - 0
Source/QuestPDF.DocumentationExamples/Text/TextBasicExamples.cs

@@ -0,0 +1,268 @@
+using System.Security.Cryptography;
+using QuestPDF.Fluent;
+using QuestPDF.Helpers;
+using QuestPDF.Infrastructure;
+
+namespace QuestPDF.DocumentationExamples.Text;
+
+public class TextBasicExamples
+{
+    [Test]
+    public void Basic()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text("Sample text");
+                });
+            })
+            .GenerateImages(x => "text-basic.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void BasicWithStyle()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(10);
+
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("Text with blue color")
+                                .FontColor(Colors.Blue.Darken1);
+
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("Bold and underlined text")
+                                .Bold()
+                                .Underline();
+
+                            column.Item()
+                                .Element(CellStyle)
+                                .Text("Centered small text")
+                                .FontSize(12)
+                                .AlignCenter();
+
+                            static IContainer CellStyle(IContainer container) =>
+                                container.Background(Colors.Grey.Lighten3).Padding(10);
+                        });
+                });
+            })
+            .GenerateImages(x => "text-basic-descriptor.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void Rich()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.AlignCenter();
+
+                            text.Span("The ");
+                            text.Span("chemical formula").Underline();
+                            text.Span(" of ");
+                            text.Span("sulfuric acid").BackgroundColor(Colors.Amber.Lighten3);
+                            text.Span(" is H");
+                            text.Span("2").Subscript();
+                            text.Span("SO");
+                            text.Span("4").Subscript();
+                            text.Span(".");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-rich.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void StyleInheritance()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(600, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .DefaultTextStyle(style => style.FontSize(20))
+                        .Column(column =>
+                        {
+                            column.Spacing(10);
+                            
+                            column.Item().Text("Products").ExtraBold().Underline().DecorationThickness(2);
+                            
+                            column.Item().Text("Comments: " + Placeholders.Sentence());
+                            
+                            column.Item()
+                                .DefaultTextStyle(style => style.FontSize(14))
+                                .Table(table =>
+                                {
+                                    table.ColumnsDefinition(columns =>
+                                    {
+                                        columns.ConstantColumn(30);
+                                        columns.RelativeColumn(1);
+                                        columns.RelativeColumn(2);
+                                    });
+                            
+                                    table.Header(header =>
+                                    {
+                                        header.Cell().Element(Style).Text("ID");
+                                        header.Cell().Element(Style).Text("Name");
+                                        header.Cell().Element(Style).Text("Description");
+
+                                        IContainer Style(IContainer container)
+                                        {
+                                            return container
+                                                .Background(Colors.Grey.Lighten3)
+                                                .BorderBottom(1)
+                                                .PaddingHorizontal(5)
+                                                .PaddingVertical(10)
+                                                .DefaultTextStyle(x => x.Bold().FontColor(Colors.Blue.Medium));
+                                        }
+                                    });
+
+                                    foreach (var i in Enumerable.Range(0, 5))
+                                    {
+                                        table.Cell().Element(Style).Text(i.ToString()).Bold();
+                                        table.Cell().Element(Style).Text(Placeholders.Label());
+                                        table.Cell().Element(Style).Text(Placeholders.Sentence());
+                                    }
+                                
+                                    IContainer Style(IContainer container)
+                                    {
+                                        return container.Padding(5);
+                                    }
+                                });
+                        });
+                });
+            })
+            .GenerateImages(x => "text-style-inheritance.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void PageNumber()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.Size(PageSizes.A5);
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Extend()
+                        .Placeholder();
+                    
+                    page.Footer()
+                        .PaddingTop(25)
+                        .AlignCenter()
+                        .Text("3 / 10");
+                        // .Text(text =>
+                        // {
+                        //     text.CurrentPageNumber();
+                        //     text.Span(" / ");
+                        //     text.TotalPages();
+                        // });
+                });
+            })
+            .GenerateImages(x => "text-page-number.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void PageNumberFormat()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.Size(PageSizes.A5);
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.CurrentPageNumber().Format(FormatWithLeadingZeros);
+                        });
+                    
+                    static string FormatWithLeadingZeros(int? pageNumber)
+                    {
+                        const int expectedLength = 3;
+                        pageNumber ??= 1;
+                        return pageNumber.Value.ToString($"D{expectedLength}");
+                    }
+                });
+            })
+            .GenerateImages(x => "text-page-number-format.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void Hyperlink()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.Size(PageSizes.A6.Landscape());
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            var hyperlinkStyle = TextStyle.Default
+                                .FontColor(Colors.Blue.Medium)
+                                .Underline();
+        
+                            text.Span("To learn more about QuestPDF, please visit its ");
+                            text.Hyperlink("homepage", "https://www.questpdf.com/").Style(hyperlinkStyle);
+                            text.Span(", ");
+                            text.Hyperlink("GitHub repository", "https://github.com/QuestPDF/QuestPDF").Style(hyperlinkStyle);
+                            text.Span(" and ");
+                            text.Hyperlink("NuGet package page", "https://www.nuget.org/packages/QuestPDF").Style(hyperlinkStyle);
+                            text.Span(".");
+                        });
+                });
+            })
+            .GeneratePdf("text-hyperlink.pdf");
+    }
+
+    
+}

+ 6 - 0
Source/QuestPDF.DocumentationExamples/Text/TextContentFormattingExamples.cs

@@ -0,0 +1,6 @@
+namespace QuestPDF.DocumentationExamples.Text;
+
+public class TextContentFormattingExamples
+{
+    
+}

+ 97 - 0
Source/QuestPDF.DocumentationExamples/Text/TextInjectContent.cs

@@ -0,0 +1,97 @@
+using QuestPDF.Fluent;
+using QuestPDF.Helpers;
+using QuestPDF.Infrastructure;
+
+namespace QuestPDF.DocumentationExamples.Text;
+
+public class TextInjectContent
+{
+    [Test]
+    public void InjectImage()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("A unit test can either ");
+                            text.Element().PaddingBottom(-4).Height(24).Image("unit-test-completed-icon.png");
+                            text.Span(" pass").FontColor(Colors.Green.Medium);
+                            text.Span(" or ");
+                            text.Element().PaddingBottom(-4).Height(24).Image("unit-test-failed-icon.png");
+                            text.Span(" fail").FontColor(Colors.Red.Medium);
+                            text.Span(".");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-inject-image.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void InjectSvg()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(350, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("To synchronize your email inbox, please click the ");
+                            text.Element().PaddingBottom(-4).Height(24).Svg("mail-synchronize-icon.svg");
+                            text.Span(" icon.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-inject-svg.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void InjectPosition()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(400, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("This ");
+    
+                            text.Element(TextInjectedElementAlignment.AboveBaseline)
+                                .Width(12).Height(12)
+                                .Background(Colors.Green.Medium);
+    
+                            text.Span(" element is positioned above the baseline, while this ");
+    
+                            text.Element(TextInjectedElementAlignment.BelowBaseline)
+                                .Width(12).Height(12)
+                                .Background(Colors.Blue.Medium);
+    
+                            text.Span(" element is positioned below the baseline.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-inject-position.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+}

+ 533 - 0
Source/QuestPDF.DocumentationExamples/Text/TextStyleExamples.cs

@@ -0,0 +1,533 @@
+using QuestPDF.Fluent;
+using QuestPDF.Helpers;
+using QuestPDF.Infrastructure;
+
+namespace QuestPDF.DocumentationExamples.Text;
+
+public class TextStyleExamples
+{
+    [Test]
+    public void FontSize()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(1000, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(10);
+
+                            column.Item()
+                                .Text("This is small text (16pt)")
+                                .FontSize(16);
+
+                            column.Item()
+                                .Text("This is medium text (24pt)")
+                                .FontSize(24);
+
+                            column.Item()
+                                .Text("This is large text (36pt)")
+                                .FontSize(36);
+                        });
+                });
+            })
+            .GenerateImages(x => "text-font-size.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void FontFamily()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(1000, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(10);
+
+                            column.Item().Text("This is text with default font (Lato)");
+
+                            column.Item().Text("This is text with Times New Roman font")
+                                .FontFamily("Times New Roman");
+
+                            column.Item().Text("This is text with Courier New font")
+                                .FontFamily("Courier New");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-font-family.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.VeryHigh, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void FontColor()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(1000, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("Each pixel consists of three sub-pixels: ");
+                            text.Span("red").FontColor(Colors.Red.Medium);
+                            text.Span(", ");
+                            text.Span("green").FontColor(Colors.Green.Medium);
+                            text.Span(" and ");
+                            text.Span("blue").FontColor(Colors.Blue.Medium);
+                            text.Span(".");
+                        });
+                    });
+            })
+            .GenerateImages(x => "text-font-color.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void BackgroundColor()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("The term ");
+                            text.Span("algorithm").BackgroundColor(Colors.Yellow.Lighten3).Bold();
+                            text.Span(" refers to a set of rules or steps used to solve a problem.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-font-background.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void Italic()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("In this sentence, the word ");
+                            text.Span("important").Italic();
+                            text.Span(" is emphasized using italics.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-font-italic.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void FontWeight()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("This sentence demonstrates ");
+                            text.Span("bold").Bold();
+                            text.Span(", ");
+                            text.Span("normal").NormalWeight();
+                            text.Span(", ");
+                            text.Span("light").Light();
+                            text.Span(" and ");
+                            text.Span("thin").Thin();
+                            text.Span(" font weights.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-font-weight.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void Subscript()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("H");
+                            text.Span("2").Subscript();
+                            text.Span("O is the chemical formula for water.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-subscript.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void Superscript()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(1000, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("E = mc");
+                            text.Span("2").Superscript();
+                            text.Span(" is the equation of mass-energy equivalence.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-superscript.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void LineHeight()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(20);
+
+                            float[] lineHeights = [0.75f, 1f, 2f];
+                            var paragraph = Placeholders.Paragraph();
+                            
+                            foreach (var lineHeight in lineHeights)
+                            {
+                                column
+                                    .Item()
+                                    .Background(Colors.Grey.Lighten3)
+                                    .Padding(5)
+                                    .Text(paragraph)
+                                    .FontSize(16)
+                                    .LineHeight(lineHeight);
+                            }
+                        });
+                });
+            })
+            .GenerateImages(x => "text-line-height.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void LetterSpacing()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(20);
+                            
+                            var letterSpacing = new[] { -0.08f, 0f, 0.2f };
+                            var paragraph = Placeholders.Sentence();
+
+                            foreach (var spacing in letterSpacing)
+                            {
+                                column
+                                    .Item()
+                                    .Background(Colors.Grey.Lighten3)
+                                    .Padding(5)
+                                    .Text(paragraph)
+                                    .FontSize(18)
+                                    .LetterSpacing(spacing);
+                            }
+                        });
+                });
+            })
+            .GenerateImages(x => "text-letter-spacing.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void WordSpacing()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Column(column =>
+                        {
+                            column.Spacing(20);
+                            
+                            var wordSpacing = new[] { -0.2f, 0f, 0.4f };
+                            var paragraph = Placeholders.Sentence();
+
+                            foreach (var spacing in wordSpacing)
+                            {
+                                column.Item()
+                                    .Background(Colors.Grey.Lighten3)
+                                    .Padding(5)
+                                    .Text(paragraph)
+                                    .FontSize(16)
+                                    .WordSpacing(spacing);
+                            }
+                        });
+                });
+            })
+            .GenerateImages(x => "text-word-spacing.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void FontFallback()
+    {
+        Settings.UseEnvironmentFonts = false;
+        
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(600, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text("The Arabic word for programming is البرمجة.")
+                        .FontFamily("Lato", "Noto Sans Arabic");
+                });
+            })
+            .GenerateImages(x => "text-font-fallback.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void FontFallbackEmoji()
+    {
+        Settings.UseEnvironmentFonts = false;
+        
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(600, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text("Popular emojis include 😊, 😂, ❤️, 👍, and 😎.")
+                        .FontFamily("Lato", "Noto Emoji");
+                });
+            })
+            .GenerateImages(x => "text-font-fallback-emoji.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void TextFontFeatures()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Row(row =>
+                        {
+                            row.Spacing(25);
+    
+                            row.RelativeItem()
+                                .Background(Colors.Grey.Lighten3)
+                                .Padding(10)
+                                .Column(column =>
+                                {
+                                    column.Item().Text("Without ligatures").FontSize(16);
+                                    
+                                    column.Item()
+                                        .Text("fly and fight")
+                                        .FontSize(32)
+                                        .DisableFontFeature(FontFeatures.StandardLigatures);
+                                });
+    
+                            row.RelativeItem()
+                                .Background(Colors.Grey.Lighten3)
+                                .Padding(10)
+                                .Column(column =>
+                                {
+                                    column.Item().Text("With ligatures").FontSize(16);
+                                    
+                                    column.Item().Text("fly and fight")
+                                        .FontSize(32)
+                                        .EnableFontFeature(FontFeatures.StandardLigatures);
+                                });
+                        });
+                });
+            })
+            .GenerateImages(x => "text-font-features.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void DecorationTypes()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("There are a couple of available text decorations: ");
+                            text.Span("underline").Underline().FontColor(Colors.Red.Medium);
+                            text.Span(", ");
+                            text.Span("strikethrough").Strikethrough().FontColor(Colors.Green.Medium);
+                            text.Span(" and ");
+                            text.Span("overline").Overline().FontColor(Colors.Blue.Medium);
+                            text.Span(". ");
+                        });
+                }); 
+            })
+            .GenerateImages(x => "text-decoration-types.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void DecorationStyles()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("Moreover, the decoration can be ");
+                            
+                            text.Span("solid").FontColor(Colors.Indigo.Medium).Underline().DecorationSolid();
+                            text.Span(", ");
+                            text.Span("double").FontColor(Colors.Blue.Medium).Underline().DecorationDouble();
+                            text.Span(", ");
+                            text.Span("wavy").FontColor(Colors.LightBlue.Medium).Underline().DecorationWavy();
+                            text.Span(", ");
+                            text.Span("dotted").FontColor(Colors.Cyan.Medium).Underline().DecorationDotted();
+                            text.Span(" or ");
+                            text.Span("dashed").FontColor(Colors.Green.Medium)
+                                .Underline().DecorationDashed();
+                            text.Span(".");
+                        });
+                }); 
+            })
+            .GenerateImages(x => "text-decoration-styles.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+    
+    [Test]
+    public void DecorationsAdvanced()
+    {
+        Document
+            .Create(document =>
+            {
+                document.Page(page =>
+                {
+                    page.MinSize(new PageSize(0, 0));
+                    page.MaxSize(new PageSize(500, 1000));
+                    page.DefaultTextStyle(x => x.FontSize(20));
+                    page.Margin(25);
+
+                    page.Content()
+                        .Text(text =>
+                        {
+                            text.Span("This text contains a ");
+                            
+                            text.Span("seriuos")
+                                .Underline()
+                                .DecorationWavy()
+                                .DecorationColor(Colors.Red.Medium)
+                                .DecorationThickness(2);
+                            
+                            text.Span(" typo.");
+                        });
+                });
+            })
+            .GenerateImages(x => "text-decoration-advanced.webp", new ImageGenerationSettings() { ImageFormat = ImageFormat.Webp, ImageCompressionQuality = ImageCompressionQuality.Best, RasterDpi = 144 });
+    }
+}

+ 1 - 0
Source/QuestPDF.DocumentationExamples/mail-synchronize-icon.svg

@@ -0,0 +1 @@
+<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><title>email-sync-outline</title><path d="M3 4C1.9 4 1 4.9 1 6V18C1 19.1 1.9 20 3 20H13.5A6.5 6.5 0 0 1 13 18H3V8L11 13L19 8V11A6.5 6.5 0 0 1 19.5 11A6.5 6.5 0 0 1 21 11.18V6C21 4.9 20.1 4 19 4H3M3 6H19L11 11L3 6M19 12L16.75 14.25L19 16.5V15C20.38 15 21.5 16.12 21.5 17.5C21.5 17.9 21.41 18.28 21.24 18.62L22.33 19.71C22.75 19.08 23 18.32 23 17.5C23 15.29 21.21 13.5 19 13.5V12M15.67 15.29C15.25 15.92 15 16.68 15 17.5C15 19.71 16.79 21.5 19 21.5V23L21.25 20.75L19 18.5V20C17.62 20 16.5 18.88 16.5 17.5C16.5 17.1 16.59 16.72 16.76 16.38L15.67 15.29Z" /></svg>

BIN
Source/QuestPDF.DocumentationExamples/unit-test-completed-icon.png


BIN
Source/QuestPDF.DocumentationExamples/unit-test-failed-icon.png