ArthurHub / ArthurHub/HTML-Renderer

Callback provided images not respecting CSS imposed size

Ouverte
#155 0 commentaires 0 réactions 0 personnes assignées Voir sur GitHub
bug
Langage dominant
C#
Étoiles
1.4k
Forks
550
Merge moyen
14 j 9 h
PR mergées (30 j)
1

Description

This is an odd case. To support SVG I am using the imageLoad event.

Basically it queries the URL supplied, constructs an instance of SvgDocument and gets height and width from attributes or the style property. Then it works out the pixel dimensions according to e.Graphics.DpiX, constructs an instance of Bitmap of this size and renders into it.

This all works, and the size is what I expect -- a QR code styled to be 20mm tall should be 472x472 pixels on a 600dpi printer, and that's exactly the size of the bitmap produced.

However, this is then drawn on the page at a size that would be correct were it a 96dpi image. This causes it to be way too big. By default bitmaps are created with this resolution so I tried setting the resolution of the bitmap to 600, but it didn't help.

Is this a bug or is there some way to make it respect the image DPI when doing layout and rendering?

imageLoad: (sender, args) =>
{
try
{
var src = args.Src;
if (src.IndexOf(':') == -1)
{
var sep = src.StartsWith("/") ? string.Empty : "/";
src = $"{baseUrl}{sep}{src}";
}
var path = Path.GetExtension(args.Src);
if (path != null && path.Equals(".svg", StringComparison.OrdinalIgnoreCase))
{
var xmlDoc = new XmlDocument();
xmlDoc.Load(src);
SvgDocument svgDoc = SvgDocument.Open(xmlDoc);
svgDoc.Ppi = (int)e.Graphics.DpiX;
if (args.Attributes.Any(attr => attr.Key.ToLower() == "style"))
{
var style = args.Attributes.Single(kvp => kvp.Key.ToLower() == "style").Value
.Split(new char[] { ':', ';' })
.Select(x => x.Trim().ToLower()).ToArray();
var i = Array.IndexOf(style, "height");
if (i > -1) { svgDoc.Height = style[i + 1].ToSvgUnit(); }
i = Array.IndexOf(style, "width");
if (i > -1) { svgDoc.Width = style[i + 1].ToSvgUnit(); }
}
int h = (int)svgDoc.Height.ToDeviceValue(null, UnitRenderingType.Other, svgDoc);
int w = (int)svgDoc.Width.ToDeviceValue(null, UnitRenderingType.Other, svgDoc);
Bitmap svgImg = new Bitmap(w, h, PixelFormat.Format32bppArgb);
svgImg.SetResolution(e.Graphics.DpiX, e.Graphics.DpiY);
svgDoc.Draw(svgImg);
args.Callback(svgImg);
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
throw;
}
}

Guide de contribution

Aucun guide de contribution indexé pour ce dépôt

Piste de recherche

Start by reproducing issue #155 with the shown imageLoad callback, an SVG styled to 20mm, and a 600dpi graphics context. Trace the image layout and rendering path to compare the 472×472 bitmap with its displayed size. Done means CSS sizing and bitmap DPI produce the intended physical size without enlarging the image.

Rédigé par le modèle d'indexation à partir du texte de l'issue.

Évaluation

Stack technique
csharp
Domaine
frontend
Type d'issue
Bug
Difficulté
4/5
Temps estimé
3-5 jours
Activité
À l'abandon
Clarté
Plutôt claire
Accessibilité débutants
35/100

Recevez les nouvelles issues par e-mail

Un résumé court des issues GitHub adaptées aux débutants.