Этот код получает различное масштабирование в зависимости от того, на каком компьютере я его запускаю.
Metafile image;
IntPtr dib;
var memoryHdc = Win32Utils.CreateMemoryHdc(IntPtr.Zero, 1, 1, out dib);
try
{
image = new Metafile(memoryHdc, EmfType.EmfOnly);
using (var g = Graphics.FromImage(image))
{
Render(g, html, left, top, maxWidth, cssData, stylesheetLoad, imageLoad);
}
}
finally
{
Win32Utils.ReleaseMemoryHdc(memoryHdc, dib);
}
В методе Render объект Metafile имеет PixelFormat DontCare и, следовательно, не имеет допустимых разрешений по вертикали или горизонтали..
Исходя из метода Render, он имеет значение Format32bppRgb
, а PhysicalDimension.Width
и PhysicalDimension.Height
увеличились для размещения визуализированного изображения.
Как я могусделать масштабирование независимым от локальных настроек?
Вот реализация CreateMemoryHdc
(я не писал, это из библиотеки OSS).
public static IntPtr CreateMemoryHdc(IntPtr hdc, int width, int height, out IntPtr dib)
{
// Create a memory DC so we can work off-screen
IntPtr memoryHdc = CreateCompatibleDC(hdc);
SetBkMode(memoryHdc, 1);
// Create a device-independent bitmap and select it into our DC
var info = new BitMapInfo();
info.biSize = Marshal.SizeOf(info);
info.biWidth = width;
info.biHeight = -height;
info.biPlanes = 1;
info.biBitCount = 32;
info.biCompression = 0; // BI_RGB
IntPtr ppvBits;
dib = CreateDIBSection(hdc, ref info, 0, out ppvBits, IntPtr.Zero, 0);
SelectObject(memoryHdc, dib);
return memoryHdc;
}
Как вы можетевидите, ширина, высота и битовая глубина, передаваемые конструктору DC, являются постоянными.Создание метафайла производит различные физические измерения.Сразу после выполнения этого
image = new Metafile(memoryHdc, EmfType.EmfOnly);
метафайл имеет PhysicalDimension.Height
(и ширину) 26,43 на моей рабочей станции и 31,25 на сервере, на котором я выполняю развертывание, поэтому разница в масштабировании уже очевидна и, следовательно, вероятноне является следствием чего-либо в рендеринге.
Это может быть актуально.BitMapInfo
определено в библиотеке OSS и выглядит следующим образом:
internal struct BitMapInfo
{
public int biSize;
public int biWidth;
public int biHeight;
public short biPlanes;
public short biBitCount;
public int biCompression;
public int biSizeImage;
public int biXPelsPerMeter;
public int biYPelsPerMeter;
public int biClrUsed;
public int biClrImportant;
public byte bmiColors_rgbBlue;
public byte bmiColors_rgbGreen;
public byte bmiColors_rgbRed;
public byte bmiColors_rgbReserved;
}
, поэтому, возможно, установка biXPelsPerMeter
и biYPelsPerMeter
поможет.Приведенный выше код не не устанавливает их и может разрешать значения платформы.
К сожалению, установка этих значений, похоже, не имеет значения.msdn говорит
biXPelsPerMeter
Горизонтальное разрешение в пикселях на метр целевого устройства для растрового изображения.Приложение может использовать это значение для выбора растрового изображения из группы ресурсов, которое наилучшим образом соответствует характеристикам текущего устройства.
Таким образом, эти настройки используются, когда загрузка растровое изображение из ресурса .Здесь ничего не поделаешь.
Все это выглядит уместно https://www.codeproject.com/articles/177394/%2fArticles%2f177394%2fWorking-with-Metafile-Images-in-NET
Может быть полезно знать, что этот код не запускается в приложении.Он отображает HTML как метафайл для печати и живет в веб-сервисе Web API.
Нет пользовательского интерфейса, поэтому я не уверен, как интерпретировать вопрос о том, поддерживает ли он DPI.Доказательства предполагают, что его DPI затронул , поэтому вопрос может быть уместным.