C# 面板显示缩放图像
我用这段代码在win窗体上绘制一个可滚动的面板。ImageBox是512x512,我使用的图像是1024x768(作为资源添加): 不幸的是,由于某些原因,图像似乎被缩放了——我无法滚动到它的边框。如果我使用512x512图像,它不适合ImageBox,它似乎被裁剪了。你知道这是怎么回事吗C# 面板显示缩放图像,c#,.net,winforms,C#,.net,Winforms,我用这段代码在win窗体上绘制一个可滚动的面板。ImageBox是512x512,我使用的图像是1024x768(作为资源添加): 不幸的是,由于某些原因,图像似乎被缩放了——我无法滚动到它的边框。如果我使用512x512图像,它不适合ImageBox,它似乎被裁剪了。你知道这是怎么回事吗 using System; using System.Drawing; using System.Windows.Forms; class ImageBox : Panel { public Ima
using System;
using System.Drawing;
using System.Windows.Forms;
class ImageBox : Panel {
public ImageBox() {
this.AutoScroll = true;
this.DoubleBuffered = true;
}
private Image mImage;
public Image Image {
get { return mImage; }
set {
mImage = value;
if (mImage != null) this.AutoScrollMinSize = mImage.Size;
else this.AutoScrollMinSize = new Size(0, 0);
this.Invalidate();
}
}
protected override void OnPaint(PaintEventArgs e) {
e.Graphics.TranslateTransform(this.AutoScrollPosition.X, this.AutoScrollPosition.Y);
if (mImage != null) e.Graphics.DrawImage(mImage, 0, 0);
base.OnPaint(e);
}
}
DrawImage有许多变体,值得仔细检查。你为你的目的选错了一个。查看MSDN上的文档: 乍一看,这听起来不错物理尺寸——这不是像素吗?但请继续阅读MSDN: 哎哟,这毕竟不是像素的问题!这是关于显示器和图像嵌入其中的分辨率。如果您希望在所有打印机上正确打印图像,例如,这是很好的 但是您希望图像的像素与显示器的像素匹配。可以根据屏幕调整图像的分辨率;但这在不同的屏幕上是行不通的。所以这个DrawImage呼叫对你不起作用 因此,您应该非常简单地使用图像的像素数,并将它们输入到右DrawImage调用中:
e.Graphics.DrawImage(mImage, 0, 0, mImage.Width, mImage.Height);
现在它不会扭曲图像,而是将一个图像像素放到一个屏幕像素上
编辑:注意:我在OP中错误引用了MSDN;现在,在第一部分中引用了正确的(但对于您来说是错误的)方法调用。DrawImage有许多变体,值得仔细检查它们。你为你的目的选错了一个。查看MSDN上的文档: 乍一看,这听起来不错物理尺寸——这不是像素吗?但请继续阅读MSDN: 哎哟,这毕竟不是像素的问题!这是关于显示器和图像嵌入其中的分辨率。如果您希望在所有打印机上正确打印图像,例如,这是很好的 但是您希望图像的像素与显示器的像素匹配。可以根据屏幕调整图像的分辨率;但这在不同的屏幕上是行不通的。所以这个DrawImage呼叫对你不起作用 因此,您应该非常简单地使用图像的像素数,并将它们输入到右DrawImage调用中:
e.Graphics.DrawImage(mImage, 0, 0, mImage.Width, mImage.Height);
现在它不会扭曲图像,而是将一个图像像素放到一个屏幕像素上
编辑:注意:我在OP中错误引用了MSDN;现在,在第一部分中引用了正确的(但对您来说是错误的)方法调用。这是图像分辨率的问题,它小于您的显示器分辨率。很不寻常 对此,有不止一种解决方法@TaW的方法可行,但有利于监视器分辨率。您将获得更清晰的图像,但它不会接近最初记录的图像大小。另一种方法是像DrawImage()一样保持物理大小,并相应地调整滚动条。将图像属性设置器更改为:
set {
mImage = value;
if (value == null) this.AutoScrollMinSize = new Size(0, 0);
else {
var size = value.Size;
using (var gr = this.CreateGraphics()) {
size.Width = (int)(size.Width * gr.DpiX / value.HorizontalResolution);
size.Height = (int)(size.Height * gr.DpiY / value.VerticalResolution);
}
this.AutoScrollMinSize = size;
}
this.Invalidate();
}
挑选“正确”的方法不是很明显,你可能应该考虑添加另一个属性,这样你可以根据需要改变它。
< P>这是一个问题,图像的分辨率,它小于你的显示分辨率。很不寻常 对此,有不止一种解决方法@TaW的方法可行,但有利于监视器分辨率。您将获得更清晰的图像,但它不会接近最初记录的图像大小。另一种方法是像DrawImage()一样保持物理大小,并相应地调整滚动条。将图像属性设置器更改为: set {
mImage = value;
if (value == null) this.AutoScrollMinSize = new Size(0, 0);
else {
var size = value.Size;
using (var gr = this.CreateGraphics()) {
size.Width = (int)(size.Width * gr.DpiX / value.HorizontalResolution);
size.Height = (int)(size.Height * gr.DpiY / value.VerticalResolution);
}
this.AutoScrollMinSize = size;
}
this.Invalidate();
}
选择“正确”的方法并不那么明显,你可能应该考虑增加另一个属性,这样你就可以根据需要修改它。请参阅“”,其中的共识是“不,他们不应该”。winform中面板的大小是多少?是设置为停靠满还是什么?我已经编辑了你的标题。请参阅“”,其中的共识是“不,他们不应该”。winform中面板的大小是多少?你是专家,但我想知道:当它以自己的尺寸绘制时,为什么图像会失真?(假设是二次像素)你是专家,但我想知道:当图像以自己的尺寸绘制时,为什么会失真?(假设为二次像素。)
set {
mImage = value;
if (value == null) this.AutoScrollMinSize = new Size(0, 0);
else {
var size = value.Size;
using (var gr = this.CreateGraphics()) {
size.Width = (int)(size.Width * gr.DpiX / value.HorizontalResolution);
size.Height = (int)(size.Height * gr.DpiY / value.VerticalResolution);
}
this.AutoScrollMinSize = size;
}
this.Invalidate();
}