如何在不使用PrinterSettings的情况下更改打印机的纸张尺寸?

时间:2015-08-11 18:36:51

标签: c# wpf printing size

我正在尝试编写一个可在特殊介质上打印的自定义标签打印机。

使用DPI 600,打印介质尺寸大约为2.00“x 0.244”。以下是带有位图标签传入值的printLabel函数。

你会看到我目前正在尝试制作自定义页面大小,但打印机打印出12个标签,只有1个具有我需要的信息。

我需要一次只打印一个标签。如果您需要更多信息或有疑问,请随时发表评论,但我对自己需要做的事情感到迷茫。< / p>

我无法想象从Windows中的打印机设置页面获取页面大小的枚举收集。任何帮助将不胜感激。

PrintServer ps = null;

        if (Properties.Settings.Default.ShrinkLabelPrinter.Contains(@"\\serverloc1") || Properties.Settings.Default.ShrinkLabelPrinter.Contains(@"\\SERVERLOC1"))
            ps = new PrintServer(@"\\serverloc1");
        else if (Properties.Settings.Default.ShrinkLabelPrinter.Contains(@"\\serverloc2") || Properties.Settings.Default.ShrinkLabelPrinter.Contains(@"\\SERVERLOC2"))
            ps = new PrintServer(@"\\serverloc2");
        else
            ps = new PrintServer();

        System.Windows.Controls.PrintDialog pd = new System.Windows.Controls.PrintDialog();

        PrintQueue queue = ps.GetPrintQueue(@"\\serverloc2\bbp33 (Copy 1)");

        List<string> lstPaperSizes = new List<string>();

        queue.CurrentJobSettings.CurrentPrintTicket.PageMediaSize = new PageMediaSize(PageMediaSizeName.Unknown, 150, 141);

        //queue.CurrentJobSettings.CurrentPrintTicket.PageMediaSize = ;

        pd.PrintQueue = queue;

        System.Drawing.Image img = label;

        //REMOVE IF LABELS ARE PORTRAIT FORMAT
        //img.RotateFlip(RotateFlipType.Rotate90FlipNone); 

        var ms = new MemoryStream();

        img.Save(ms, System.Drawing.Imaging.ImageFormat.Png);
        ms.Position = 0;

        var bi = new BitmapImage();
        bi.BeginInit();
        bi.CacheOption = BitmapCacheOption.OnLoad;
        bi.StreamSource = ms;
        RenderOptions.SetBitmapScalingMode(bi, BitmapScalingMode.HighQuality);
        bi.EndInit();

        var vis = new DrawingVisual();
        var dc = vis.RenderOpen();

        Rect angle = new Rect
        {
            Width = Convert.ToInt32(Math.Round(bi.Width, 0)),
            Height = Convert.ToInt32(Math.Round(bi.Height, 0))
        };

        dc.DrawImage(bi, angle);
        dc.Close();
        img.Save(@"\temp\Label Creator\Resources\cable_label.png");
        pd.PrintVisual(vis, "Cable Label");

1 个答案:

答案 0 :(得分:4)

我建议你做更多的调试,检查图像的高度,检查你的页面大小是否正确,等等。总之,它可能是很多东西;这里引起了我的注意:

  1. 您要打印的PageMediaSize是1.5625&#34; (150px / 96dpi)宽,1.46875&#34; (141px / 96dpi)高
  2. 而不是更改queue.CurrentJobSettings...PageMediaSize尝试执行pd.PrintTicket.PageMediaSize.PageMediaSize = new ...
  3. 也许PrintQueue.Commit()对您有用
  4. 设置断点并查看您的PrintQueue属性,如果我建议无效,我有兴趣查看PrintQueue.UserPrintTicket的值(但您可能不想要改变UserPrintTicket)。
  5. 确保您了解打印机本身及其硬件功能。它是做风景和肖像吗?它有SDK吗?
  6. 查看/研究PrintQueue.PrintCapabilities然后断点+调试目标打印机的功能至少一次。那里有很多信息(如兼容的媒体大小)。
  7. 请注意img的尺寸。如果你想要2&#34;你的媒体大小应该是new PageMediaSize(PageMediaSizeName.Unknown, 192, 23.424);。 x 0.244&#34;。您的图片应该具有相似的尺寸,不应该超过这些尺寸。打印前请查看pd.PrintableAreaHeight|Width
    • Windows显示默认为96DPI。将视觉效果发送到打印机时,会假设这种情况。因此,您可以通过(size in inches / 96) = # of pixels you want to use with PageMediaSize找到您的维度。转到标准打印机并查看 - 通过PrintCapabilities - 大小为PageMediaSizeName.NorthAmericanLetter,您将看到高度为816像素x 1056像素。 816/96 = 8.5,1056 / 96 = 11 - 8.5 x 11媒体。
  8. 您还可以下载XML格式的打印机功能。在XML中,您可能会发现打印机可以处理的其他功能(如介质尺寸),并且可能需要您在打印前进行设置。
  9. 我非常自信地研究和尝试我在大胆项目中指出的事情应该会引导你在某个时候找到解决方案。在我使用System.Printing命名空间的许多小时内,我发现每台打印机的行为都不同,小的变化可以产生最大的影响!

    我会四处寻求帮助,只需在评论中发帖!祝好运。

    修改1

    不幸的是,我没有任何自定义/专业打印机可供测试,但我会采取一些方法来获取预定义的尺寸。

    使用PrintQueue.PrintCapabilities

    这将打印出打印机报告的功能大小。由于B33-126是自定义尺寸,因此您可能会看到一堆具有尺寸的PageMediaSizeName.Unknown,您必须在其中标识适合您的尺寸,然后在您的PrintTicket中使用相同尺寸应用

    PrintQueue pq = GetYourPrintQueue();
    PrintCapabilities pc = pq.GetPrintCapabilities();
    ReadOnlyCollection<PageMediaSize> capableSizes = pc.PageMediaSizeCapability;
    foreach(var pm in capableSizes) 
    { 
        Console.WriteLine(pm);
    }
    //Identify what PageMediaSize you need, and set your print ticket to use the exact same dimensions
    

    使用PrintQueue.GetPrintCapabilitiesAsXml()

    PrintQueue pq = GetYourPrintQueue();
    MemoryStream pcXml = pq.GetPrintCapabilitiesAsXml();
    Console.WriteLine(pcXml.ToString())
    //At this point, set a breakpoint on Console.WriteLine and inspect the `pcXml` object to see if the XML contains custom print capabilities.  If so you'll have to identify which sizes/properties you need to make use of.
    

    使用PrintQueue.UserPrintTicket

    UserPrintTicket是当前用户的默认打印机设置。因此,您可以使用控制面板进入打印设备,右键单击目标打印机,然后转到&#34;打印首选项&#34;并将您的Page / Paper尺寸更改为B33-126尺寸,然后单击Apply / Okay关闭窗口。

    现在做:

    PrintQueue pq = GetYourPrintQueue();
    var upt = pq.UserPrintTicket;
    Console.WriteLine(upt);
    

    并在Console.WriteLine上设置断点并检查upt。这将显示PrintTicket中的当前设置,这些设置与我们在上述步骤中设置/应用的设置相匹配。您应该可以pd.PrintTicket = upt进行打印并打印出来。

    使用PrintDialog:

    您可以使用PrintDialog.ShowDialog()设置打印机设置,然后添加断点以查看它们的内容并将相同的设置应用于您的解决方案。

    PrintDialog pd = new PrintDialog();
    pd.ShowDialog();
    //Set a breakpoint on the code show below this comment.  At this point your print dialog is shown and you can select a printer.  Select the target printer and click "Preferences." When shown, set whatever settings you might normally use to print labels.  Then click "Apply," then click "OK."  
    Console.WriteLine(pd.PrintTicket);
    

    当调试器到达最后一行代码时,您刚刚通过首选项页面应用于打印机的设置将显示在pd.PrintTicket中。您可以对应用程序中的PrintTicket进行这些设置并使用相同的设置。

    最后一个注意事项是关闭PrintDialog后的属性。它有你的高度和宽度(可以找到边距)。您希望确保您尝试打印的图像适合这些尺寸。请记住,您可以使用PrintDialog.CopyCount打印倍数。