diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml
index a76991f76..9335d30d9 100644
--- a/.github/workflows/build.yml
+++ b/.github/workflows/build.yml
@@ -1,4 +1,4 @@
-name: Build
+name: Build, Package & Publish
on: [push, pull_request, workflow_dispatch]
@@ -23,7 +23,7 @@ jobs:
fail-fast: false
matrix:
platform:
- - { name: Windows x64, os: windows-2025 }
+ - { name: Windows x64, os: windows-2025-vs2026 }
- { name: Ubuntu x64, os: ubuntu-24.04 }
- { name: macOS arm64, os: macos-15 }
dotnet:
@@ -33,11 +33,11 @@ jobs:
steps:
- name: Checkout HTML Renderer
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Setup .NET ${{ matrix.dotnet.version }} SDK
id: setup-dotnet
- uses: actions/setup-dotnet@v5
+ uses: actions/setup-dotnet@v6
with:
dotnet-version: ${{ matrix.dotnet.version }}
- name: Enforce SDK Version
@@ -45,11 +45,42 @@ jobs:
- name: Verify SDK Installation
run: dotnet --info
+ - name: Select build target
+ id: build-target
+ run: |
+ # HtmlRenderer.WinUI/HtmlRenderer.Demo.WinUI (Windows App SDK/Win2D, MSIX PRI generation via
+ # native makepri.exe/makeappx.exe) can only build on Windows - unlike the WinForms/WPF adapters,
+ # which cross-compile cleanly everywhere via EnableWindowsTargeting's reference-assembly story,
+ # there is no non-Windows equivalent for those native tools at all. Non-Windows runners build a
+ # solution filter excluding just those two projects; everything else still builds and tests
+ # identically on every OS.
+ $target = $IsWindows ? "Source/HtmlRenderer.sln" : "Source/HtmlRenderer.CrossPlatform.slnf"
+ echo "path=$target" >> $env:GITHUB_OUTPUT
+
- name: Restore Dependencies
- run: dotnet restore Source/HtmlRenderer.sln
+ run: dotnet restore ${{ steps.build-target.outputs.path }}
- name: Build
- run: dotnet build Source/HtmlRenderer.sln --configuration Release --no-restore
+ run: dotnet build ${{ steps.build-target.outputs.path }} --configuration Release --no-restore
+
+ - name: Run Tests
+ if: runner.os == 'Windows'
+ run: dotnet test Source/HtmlRenderer.sln --configuration Release --no-build --logger trx --results-directory ${{ github.workspace }}/TestResults
+ env:
+ PDF_OUTPUT_DIRECTORY: ${{ github.workspace }}/pdf-artifacts/${{ matrix.platform.name }}-${{ matrix.dotnet.name }}
+ HTML_RENDERER_REGRESSION_OUTPUT_DIRECTORY: ${{ github.workspace }}/image-regression/${{ matrix.platform.name }}-${{ matrix.dotnet.name }}
+
+ - name: Run Tests
+ if: runner.os != 'Windows'
+ run: |
+ $failed = $false
+ Get-ChildItem -Path Source/Test -Recurse -Filter *.Test.csproj | ForEach-Object {
+ dotnet test $_.FullName --configuration Release --no-build --logger trx --results-directory ${{ github.workspace }}/TestResults
+ if ($LASTEXITCODE -ne 0) { $failed = $true }
+ }
+ if ($failed) { exit 1 }
+ env:
+ PDF_OUTPUT_DIRECTORY: ${{ github.workspace }}/pdf-artifacts/${{ matrix.platform.name }}-${{ matrix.dotnet.name }}
- name: Create HtmlRenderer.Core NuGet package
run: dotnet pack Source/HtmlRenderer/HtmlRenderer.csproj --configuration Release --include-symbols -p:SymbolPackageFormat=snupkg --no-build --verbosity normal --output ${{ env.NuGetDirectory }}
@@ -64,11 +95,27 @@ jobs:
run: dotnet pack Source/HtmlRenderer.WPF/HtmlRenderer.WPF.csproj --configuration Release --include-symbols -p:SymbolPackageFormat=snupkg --no-build --verbosity normal --output ${{ env.NuGetDirectory }}
- name: Upload NuGet package artifacts
- uses: actions/upload-artifact@v5
+ uses: actions/upload-artifact@v7
with:
name: "HTML Renderer (${{ matrix.platform.name }} ${{ matrix.dotnet.name }})"
path: ${{ env.NuGetDirectory }}/*.*nupkg
+ - name: Upload PDF artifacts
+ if: always()
+ uses: actions/upload-artifact@v7
+ with:
+ name: "PDF artifacts (${{ matrix.platform.name }} ${{ matrix.dotnet.name }})"
+ path: ${{ github.workspace }}/pdf-artifacts/**/*.pdf
+ if-no-files-found: ignore
+
+ - name: Upload image regression artifacts
+ if: always()
+ uses: actions/upload-artifact@v7
+ with:
+ name: "Image regression artifacts (${{ matrix.platform.name }} ${{ matrix.dotnet.name }})"
+ path: ${{ github.workspace }}/image-regression/**/*.png
+ if-no-files-found: ignore
+
- name: NuGet Login
if: startsWith(github.ref, 'refs/tags/') && matrix.dotnet.name == '.NET 8' && runner.os == 'Windows'
uses: NuGet/login@v1
diff --git a/.gitignore b/.gitignore
index ec0fb2754..aa314ccc9 100644
--- a/.gitignore
+++ b/.gitignore
@@ -5,6 +5,9 @@
# mstest test results
TestResults
+# Rider
+.idea/
+
## Ignore Visual Studio temporary files, build results, and
## files generated by popular Visual Studio add-ons.
diff --git a/LICENSE b/LICENSE
index 0041d48b4..6b90a0b8d 100644
--- a/LICENSE
+++ b/LICENSE
@@ -1,5 +1,5 @@
Copyright (c) 2009, José Manuel Menéndez Poo
-Copyright (c) 2013-2025, Arthur Teplitzki
+Copyright (c) 2013-2026, Arthur Teplitzki
All rights reserved.
Redistribution and use in source and binary forms, with or without modification,
diff --git a/README.md b/README.md
index f689bdfac..0a8553037 100644
--- a/README.md
+++ b/README.md
@@ -16,7 +16,7 @@ For documentation, check out the project on the [CodePlex Archive](https://codep
## Download
-The release packages on [GitHub](https://github.com/ArthurHub/HTML-Renderer/releases) or the [CodePlex Archive](https://codeplexarchive.org/project/HtmlRenderer) also contains a Demo application to explore HML Renderer's capabilities.
+The release packages on [GitHub](https://github.com/ArthurHub/HTML-Renderer/releases) also contain a Demo application to explore HML Renderer's capabilities.
The latest NuGet packages can be found on NuGet.org:
diff --git a/Source/Demo/Common/DemoUtils.cs b/Source/Demo/Common/DemoUtils.cs
index 682f325f5..a14b33b3f 100644
--- a/Source/Demo/Common/DemoUtils.cs
+++ b/Source/Demo/Common/DemoUtils.cs
@@ -74,8 +74,8 @@ public static string GetStylesheet(string src)
a:link { text-decoration: none; }
a:hover { text-decoration: underline; }
.gray { color:gray; }
- .example { background-color:#efefef; corner-radius:5px; padding:0.5em; }
- .whitehole { background-color:white; corner-radius:10px; padding:15px; }
+ .example { background-color:#efefef; border-radius:5px; padding:0.5em; }
+ .whitehole { background-color:white; border-radius:10px; padding:15px; }
.caption { font-size: 1.1em }
.comment { color: green; margin-bottom: 5px; margin-left: 3px; }
.comment2 { color: green; }";
diff --git a/Source/Demo/Common/HtmlPrettyPrinter.cs b/Source/Demo/Common/HtmlPrettyPrinter.cs
new file mode 100644
index 000000000..09d0e207d
--- /dev/null
+++ b/Source/Demo/Common/HtmlPrettyPrinter.cs
@@ -0,0 +1,145 @@
+// "Therefore those skilled at the unorthodox
+// are infinite as heaven and earth,
+// inexhaustible as the great rivers.
+// When they come to an end,
+// they begin again,
+// like the days and months;
+// they die and are reborn,
+// like the four seasons."
+//
+// - Sun Tsu,
+// "The Art of War"
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Text;
+using HtmlKit;
+
+namespace TheArtOfDev.HtmlRenderer.Demo.Common
+{
+ ///
- Case 1
Text align justify with background colors
- Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur ornare mollis elit. Integer sagittis. Fusce elementum commodo felis. Vivamus lacinia eleifend libero. Donec - lacus. Nam sit amet urna. Nullam nulla. Donec accumsan porta magna. Mauris a dolor eu elit rutrum commodo. Nam iaculis turpis non augue. Nullam lobortis egestas risus. Nulla + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur ornare mollis elit. Integer sagittis. Fusce elementum commodo felis. Vivamus lacinia eleifend libero. Donec + lacus. Nam sit amet urna. Nullam nulla. Donec accumsan porta magna. Mauris a dolor eu elit rutrum commodo. Nam iaculis turpis non augue. Nullam lobortis egestas risus. Nulla elementum dolor ac mauris. Ut tristique. In varius volutpat metus. Integer leo dolor, tristique a, dignissim ac, iaculis eget, elit. Donec arcu.
-
-
+ + Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur ornare mollis elit. Integer_sagittis_Fusce_elementum_commodo_felis_Vivamus_lacinia_eleifend_libero_Donec lacus. -
+ בדיקה של טקסט ימין לשמאל +
++ בדיקה של טקסט ימין לשמאל normal text +
-
- בדיקה של טקסט ימין לשמאל -
-- בדיקה של טקסט ימין לשמאל normal text -
-- בדיקה של טקסט ימין לשמאל normal text -
+ בדיקה של טקסט ימין לשמאל normal text - \ No newline at end of file +