当按钮大小正确缩放(34×33)时,按钮大小中的图像不会缩放/拉伸/缩放(它仍然是16×16).我做了很多尝试来解决这个问题:
>父控件AutoScaleMode设置为Font,将其设置为Dpi不会使其工作.
>将AutoSize设置按钮设置为true或false不会使其正常工作.
>将按钮或父controlAutoSizeMode设置为任何值都不起作用.
>没有可以设置为拉伸或缩放的Button.ImageLayout.
>使用新的App.Config设置< add key =“EnableWindowsFormsHighDpiAutoResizing”value =“true”/>不起作用.
>更改按钮FlatStyle或ImageAlign不起作用.
你是如何在你的应用中解决这个问题的?
这是代码:
public static IEnumerable<Idisposable> AdjustControlsThroughDPI(this Control.ControlCollection controls) {
Debug.Assert(controls != null);
if (DPIRatioIsOne) {
return new Idisposable[0]; // No need to adjust on DPI One
}
var list = new List<Idisposable>();
foreach (Control control in controls) {
if (control == null) { continue; }
var button = control as ButtonBase;
if (button != null) {
button.AdjustControlsThroughDPI(list);
continue;
}
// Here more controls tahn button can be adjusted if needed...
// Recursive
var nestedControls = control.Controls;
Debug.Assert(nestedControls != null);
if (nestedControls.Count == 0) { continue; }
var disposables = nestedControls.AdjustControlsThroughDPI();
list.AddRange(disposables);
}
return list;
}
private static void AdjustControlsThroughDPI(this ButtonBase button,IList<Idisposable> list) {
Debug.Assert(button != null);
Debug.Assert(list != null);
var image = button.Image;
if (image == null) { return; }
var imagestretched = image.GetimagestretchedDPI();
button.Image = imagestretched;
list.Add(imagestretched);
}
private static Image GetimagestretchedDPI(this Image imageIn) {
Debug.Assert(imageIn != null);
var newWidth = imageIn.Width.MultipliedByDPIRatio();
var newHeight = imageIn.Height.MultipliedByDPIRatio();
var newBitmap = new Bitmap(newWidth,newHeight);
using (var g = Graphics.FromImage(newBitmap)) {
// According to this blog post http://blogs.msdn.com/b/visualstudio/archive/2014/03/19/improving-high-dpi-support-for-visual-studio-2013.aspx
// NearestNeighbor is more adapted for 200% and 200%+ DPI
var interpolationMode = InterpolationMode.HighQualityBicubic;
if (s_DPIRatio >= 2.0f) {
interpolationMode = InterpolationMode.NearestNeighbor;
}
g.InterpolationMode = interpolationMode;
g.DrawImage(imageIn,new Rectangle(0,newWidth,newHeight));
}
imageIn.dispose();
return newBitmap;
}
请注意,返回了创建的可枚举的一次性位图.如果您不关心在按钮上处理位图,则不必关心处理拉伸位图.
请注意我们处理原始按钮位图.
注意我们自己的成员来处理DPI:MultipliedByDPIRatio(this int),DPIRatioIsOne:bool,s_DPIRatio.你可以写自己的,棘手的一点是获得实际的DPI比率.为了收集DPI比率,我找到的最好的方法是this one.
请注意对博客文章Improving High-DPI support for Visual Studio 2013的引用,其中VS团队解释说,对于他们的图标样式,他们确定图像延伸到200%,100%[最好用Bicubic算法实现,并且高于或等于200%,最好实现与朴素最近邻算法.提供的代码反映了这些选择.
编辑:在200%DPI下的各种插值模式的屏幕截图下,IMHO InterpolationMode.HighQualityBicubic优于InterpolationMode.NearestNeighbor.