确认,打印图形位置C#

确认,打印图形位置C#,c#,winforms,printing,C#,Winforms,Printing,我创建了下面的代码,以帮助我将管理表单打印为类似“报告”的文档,显示文档所需的日期和图形 try { Graphics g = this.CreateGraphics(); AdminPage = new Bitmap(Size.Width, Size.Height, g); Graphics Printed = Graphics.FromImage(AdminPage); Pri

我创建了下面的代码,以帮助我将管理表单打印为类似“报告”的文档,显示文档所需的日期和图形

  try
        {
            Graphics g = this.CreateGraphics();
            AdminPage = new Bitmap(Size.Width, Size.Height, g);
            Graphics Printed = Graphics.FromImage(AdminPage);
            Printed.CopyFromScreen(519, 340, 0,0,this.Size);//519,340 this.Location.Y,this.Location.X
            printPreviewAdminDialogue.ShowDialog();
        }
        catch(Exception )
        {
            MessageBox.Show("Please check printer connection!");
        }
我使用了屏幕的坐标数据,如下所示:

Printed.CopyFromScreen(519, 340, 0,0,this.Size);
这在任何尺寸的屏幕上都能正常工作,还是会导致其他设备(而不仅仅是我的笔记本电脑)出现格式问题


到目前为止,它看起来很好

此方法接受控件(
SourceControl
)引用,并返回控件窗口的屏幕截图产生的位图。

参数:

源控件
:要打印的控件。它可以是顶级窗口(窗体)或子控件。

Dpi
:生成位图的Dpi分辨率。

ScaleToDpi
:如果设置为
true
,位图的大小将被缩放以匹配Dpi参数,从而定义相对于当前屏幕分辨率的缩放因子。例如:如果参数
Dpi
=300且当前屏幕分辨率为96 Dpi,则生成的位图大小将按3.125的系数缩放

ClientAreaOnly
:如果为true,则捕获
SourceControl
客户端区域,否则捕获整个窗口边界

插值模式
:定义缩放位图的结果质量。对于放大,
Bicubic
HighQualityBicubic
提供更好的结果<代码>双三次可以渲染整形器图像。此参数的有用性取决于图像的使用方式。在纸张上打印图像时,可感知的视觉质量可能不同。打印时,图像越清晰效果越好。


可以使用
PrintPreviewControl
测试结果,以查看缩放位图和非缩放位图之间的差异。

以300 DPI的分辨率打印包含边框的表单,但不按新分辨率缩放(仅修改生成的位图分辨率):

以300 DPI的分辨率打印表单ClientArea,并使用
HighQualityBicubic
Interpolation:

Bitmap ClientArea300DpiScaled = PrintControlFromScreen(this, true, 300, true, InterpolationMode.HighQualityBicubic);
Bitmap Child96DpiUnscaled = PrintControlFromScreen(this.button1, true, 96, false, InterpolationMode.Bilinear);
相同,但它使用双线性插值打印分辨率为96 DPI的
按钮1
控件的客户区:

Bitmap ClientArea300DpiScaled = PrintControlFromScreen(this, true, 300, true, InterpolationMode.HighQualityBicubic);
Bitmap Child96DpiUnscaled = PrintControlFromScreen(this.button1, true, 96, false, InterpolationMode.Bilinear);

更新1(打印预览示例):

这是显示位图打印预览的一种可能方式。当然,它应该适合实际的打印机。这是一般用途。

在按钮事件处理程序中创建位图,并显示打印预览对话框以查看结果。

这将以当前形式创建PictureBox控件的屏幕截图 (此选项)仅获取客户端区域,将结果设置为300Dpi,是否执行 不缩放图像(保持屏幕原始大小),使用双三次曲线 用于渲染的插值。

这是按钮单击处理程序,从中可以调用
PrintControlFromScreen()
方法:

private void button1_Click(object sender, EventArgs e)
{
    Bitmap screenCapture = PrintControlFromScreen(this.pictureBox1, true, 300, false, InterpolationMode.Bicubic);

    PrintDocument PrintDoc = new PrintDocument();
    PrintDoc.DocumentName = "ScreenShot";
    PrintDoc.DefaultPageSettings.PrinterResolution = new PrinterResolution() { X = 300, Y = 300 };
    PrintDoc.DefaultPageSettings.Landscape = PrintDoc.DefaultPageSettings.PaperSize.Width < screenCapture.Width;
    PrintDoc.OriginAtMargins = true;

    PrintDoc.PrintPage += (s, ppe) =>
    {
        Rectangle BitmapSize = new Rectangle(new Point(0, 0),
                               new Size(screenCapture.Width, screenCapture.Height));

        Graphics _imagegraph = Graphics.FromImage(screenCapture);
        _imagegraph.CompositingMode = CompositingMode.SourceCopy;
        _imagegraph.CompositingQuality = CompositingQuality.HighQuality;
        _imagegraph.SmoothingMode = SmoothingMode.HighQuality;
        _imagegraph.PixelOffsetMode = PixelOffsetMode.HighQuality;
        _imagegraph.InterpolationMode = InterpolationMode.HighQualityBicubic;

        ImageAttributes ImageAttr = new ImageAttributes();
        ImageAttr.ClearThreshold(ColorAdjustType.Bitmap);

        ppe.Graphics.DrawImage(screenCapture, BitmapSize, 0F, 0F,
                               BitmapSize.Width, BitmapSize.Height, GraphicsUnit.Pixel, ImageAttr);
    };

    PrintPreviewDialog pPreviewDiag = new PrintPreviewDialog();
    pPreviewDiag.Document = PrintDoc;
    pPreviewDiag.AutoScaleDimensions = new SizeF(Screen.PrimaryScreen.BitsPerPixel * 1.5F,
                                                 Screen.PrimaryScreen.BitsPerPixel * 1.5F);
    pPreviewDiag.AutoScaleMode = AutoScaleMode.Dpi;
    pPreviewDiag.StartPosition = FormStartPosition.CenterScreen;
    pPreviewDiag.ShowDialog();
}
private void按钮1\u单击(对象发送者,事件参数e)
{
位图截屏=PrintControlFromScreen(this.pictureBox1,true,300,false,InterpolationMode.Bicubic);
PrintDocument PrintDoc=新的PrintDocument();
PrintDoc.DocumentName=“屏幕截图”;
PrintDoc.DefaultPageSettings.PrinterResolution=新的PrinterResolution(){X=300,Y=300};
PrintDoc.DefaultPageSettings.Landscape=PrintDoc.DefaultPageSettings.PaperSize.Width
{
矩形位图大小=新矩形(新点(0,0),
新尺寸(截屏宽度、截屏高度);
Graphics _imagegraph=Graphics.FromImage(截屏);
_imagegraph.CompositingMode=CompositingMode.SourceCopy;
_imagegraph.CompositingQuality=CompositingQuality.HighQuality;
_imagegraph.SmoothingMode=SmoothingMode.HighQuality;
_imagegraph.PixelOffsetMode=PixelOffsetMode.HighQuality;
_imagegraph.InterpolationMode=InterpolationMode.HighQualityBicubic;
ImageAttributes ImageAttr=新的ImageAttributes();
ImageAttr.ClearThreshold(ColorAdjustType.Bitmap);
ppe.Graphics.DrawImage(截屏、位图大小、0F、0F、,
BitmapSize.Width、BitmapSize.Height、GraphicsUnit.Pixel、ImageAttr);
};
PrintPreviewDialog pPreviewDiag=新的PrintPreviewDialog();
pPreviewDiag.Document=PrintDoc;
pPreviewDiag.AutoScaleDimensions=新的SizeF(Screen.PrimaryScreen.BitsPerPixel*1.5F,
Screen.PrimaryScreen.BitsPerPixel*1.5F);
pPreviewDiag.AutoScaleMode=AutoScaleMode.Dpi;
pPreviewDiag.StartPosition=FormStartPosition.CenterScreen;
pPreviewDiag.ShowDialog();
}

Create
RDLC
报告并打印它。
CreateGraphics
几乎总是不正确的。应该改用Printed.DrawToBitmap()。现在,如果你没有将你的应用程序声明为dpiAware,那么你就有可能关闭屏幕截图;如果另一个窗口与你的窗口重叠,那么你可能会得到错误的内容。也很难猜到为什么您硬编码了位置而不使用这个.PointToScreen(Printed.location)。由于重新缩放和不适当的抗锯齿,打印输出看起来会很难看,这需要另一种方法。@pink:实际上这是一个例外:位图构造函数可以使用图形对象为其提供位图的dpi。所以这可能很好。前几天,我给了你一个可能的解决方案。但,正如我现在看到的,它可能并没有达到目标,因为我并没有注意到您需要打印(可控)版本的屏幕截图。试试另一个,它更适合印刷。
private void button1_Click(object sender, EventArgs e)
{
    Bitmap screenCapture = PrintControlFromScreen(this.pictureBox1, true, 300, false, InterpolationMode.Bicubic);

    PrintDocument PrintDoc = new PrintDocument();
    PrintDoc.DocumentName = "ScreenShot";
    PrintDoc.DefaultPageSettings.PrinterResolution = new PrinterResolution() { X = 300, Y = 300 };
    PrintDoc.DefaultPageSettings.Landscape = PrintDoc.DefaultPageSettings.PaperSize.Width < screenCapture.Width;
    PrintDoc.OriginAtMargins = true;

    PrintDoc.PrintPage += (s, ppe) =>
    {
        Rectangle BitmapSize = new Rectangle(new Point(0, 0),
                               new Size(screenCapture.Width, screenCapture.Height));

        Graphics _imagegraph = Graphics.FromImage(screenCapture);
        _imagegraph.CompositingMode = CompositingMode.SourceCopy;
        _imagegraph.CompositingQuality = CompositingQuality.HighQuality;
        _imagegraph.SmoothingMode = SmoothingMode.HighQuality;
        _imagegraph.PixelOffsetMode = PixelOffsetMode.HighQuality;
        _imagegraph.InterpolationMode = InterpolationMode.HighQualityBicubic;

        ImageAttributes ImageAttr = new ImageAttributes();
        ImageAttr.ClearThreshold(ColorAdjustType.Bitmap);

        ppe.Graphics.DrawImage(screenCapture, BitmapSize, 0F, 0F,
                               BitmapSize.Width, BitmapSize.Height, GraphicsUnit.Pixel, ImageAttr);
    };

    PrintPreviewDialog pPreviewDiag = new PrintPreviewDialog();
    pPreviewDiag.Document = PrintDoc;
    pPreviewDiag.AutoScaleDimensions = new SizeF(Screen.PrimaryScreen.BitsPerPixel * 1.5F,
                                                 Screen.PrimaryScreen.BitsPerPixel * 1.5F);
    pPreviewDiag.AutoScaleMode = AutoScaleMode.Dpi;
    pPreviewDiag.StartPosition = FormStartPosition.CenterScreen;
    pPreviewDiag.ShowDialog();
}