cancel
Showing results for 
Search instead for 
Did you mean: 

Crystal Reports prints to default printer no matter what

Former Member
0 Kudos

We have a .NET/C# application and we upgraded from Crystal v10.2 to v13 recently.

With the v10.2 we used the .NET API. After upgrade we experience a problem: no matter how I we to set the printer name (to the selected printer by user) before printing Crystal prints to the default printer. There are strange exceptions, for example mostly I can print to my local "Microsoft XPS Document Writer", so somehow that can override the stubborn behavior (but not always!). When I try to print to my local "Send to OneNote 2010" printer or other printer however, the report is printed to our default network printer for sure.

When I debug our code with Visual Studio 2012, I can clearly see that:

1. With .NET API: the Crystal ReportDocument object's PrintOptions object's PrinterName property is an empty string, and when I try to assign the desired printer name (like "Send to OneNote 2010"), it simply ignores my try. This is even true if I try to manipulate the object in the debugger or in the Immediate Window.

2. I tried the RAS API too. I can query the RAS object (which has the type of CrystalDecisions.ReportAppServer.ClientDoc.ReportClientDocument) from the .NET ReportDocument, I guess the .NET API just wraps around the RAS objects. I see that the PrinterName is empty there too. I try to manipulate it through the PrintOutputController, like:

boReportClientDocument.PrintOutputController.ModifyPrinterName("Send to OneNote 2010");

but that try fails either.

About our reports (.rpt files): we should have the "No Printer" checked in all of them (we have like 300 reports in our apps). Now it seems that some of them doesn't have that set, but in those cases changing that would cause problems with our clients. The editor we use doesn't show the "Dissociate Formatting Page size and printer" checkbox in "File/Page Setup".

Accepted Solutions (1)

Accepted Solutions (1)

0 Kudos

You have to use the Windows.system Printer info.

See attached sample for how to ( ras2k8PrinterSimple1.txt )... Rename the file to .zip and extract.

It's not complete and some routines are only partially working, it's in progress....

Also, SP 5 is now available.

Don

Former Member
0 Kudos

Hi Don. I tell you what was the solution finally. Thanks for the source but I haven't compiled it because it needed v10.2 Crystal and at the same time I dig deep enough in our source to uncover some facts. Apparently the "No Printer" checkbox in the reports is very important regarding this issue, and it is the culprit (kinda).

I want to make things more precise.

Our old code with Crystal v10.2 used ICrystalReportDocument interface PrintToPrinter(int,bool,int,int) function and CrystalDecisions.CrystalReports.Engine.ReportDocument to print:

_reportDocument.PrintToPrinter(numCopies, isCollated, startPageN, endPageN);

That stopped working after switching to v13 Crystal, the ReportDocument's ReportOptions object wouldn't ever accpet any PrinterName any more, and it'd show empty string in it. I tried to call the other mutations of PrintToPrinter, which is not present on the interface itself but it can be called on the document (there are two of them, and someone can specify DissociateFormattingPageSizeAndPrinter boolean and stuff, but that wouldn't help either. I played with the dissociate paranmeter too, but the margins were screwed up in true and false settings too.

I tried a mixture of RAS/.NET API code, I followed the "NET-CS2005-RAS-Managed BE12 Print Report.zip" example http://scn.sap.com/docs/DOC-6391

boReportClientDocument.PrintOutputController.ModifyPrinterName(@"\\ourdevserver\devprinter");

//Print the report.

boReportClientDocument.PrintOutputController.PrintReport(null);

I say that this is a mixed technique for me, because I obtain the ReportClientDocument from the CrystalDecisions.CrystalReports.Engine.ReportDocument. Unfortunately that didn't work either. I tried the other way suggested in the "NET-CS2005-RAS-Managed BE12 Print Report.zip" too (query out the whole report options shebang, change the wanted value and set the whole shebang back). I couldn't still force to set the printer name.

So the trick is first to fling a chicken around in the air and sacrifice a goat.

Then what someone should do in this case is to construct a CrystalDecisions.ReportAppServer.Controllers.PrintReportOptions, fill it in (including the PrinterName, but here can come the collation, and other parameters present in the PrintToPrinter call). So it goes somthing like that:

PrintReportOptions printReportOptions = new PrintReportOptions();

if (pPrinterSettings.PrintRange == PrintRange.SomePages)

{

  printReportOptions.AddPrinterPageRange(pPrinterSettings.FromPage, pPrinterSettings.ToPage);

}

printReportOptions.NumberOfCopies = printerSettings.Copies;

printReportOptions.Collated = printerSettings.Collate;

printReportOptions.PrinterName = printerSettings.PrinterName;

printReportOptions.PaperSize = ReportPrintOptions.convertFromNativePaperKindToRASPaperSize(pageSettings.PaperSize.Kind);

printReportOptions.PaperSource = ReportPrintOptions.convertFromNativePaperSourceKindToRASPaperSource(pageSettings.PaperSource.Kind);

printReportOptions.PrinterDuplex = ReportPrintOptions.convertFromNativeDuplexToRASPrinterDuplex(printerSettings.Duplex);

_reportDocument.ReportClientDocument.PrintOutputController.PrintReport(printReportOptions);

As you can also see, now I have a set of enum converter functions not just for the CrystalDecision .NET API enums to the System enums (PaperSize, PaperSource and PrinterDuplexity), but now fo rthe RAS API too. Is there an automatic way to do that. I see that there are some CopyTo and CopyFrom, but I couldn't find one in this direction.

Epilogue: historically most of our ~300+ reports has the "No Printer" (screen optimized) checked. I'm sure there is a reason which would pop-up only if we'd change that switch and break something on the customer side. But we won't break there anything, so we won't change that. In the v10.2 Crystal we could print these reports wherever we wanted, but that thing broke with the v13 Crystal. Apparently we found a way to work it around. Something changed under the hood of Crystal (why this got broken), and I can just hope, pray that the current functionality won't be broken. I'm still not convinced that the margins are 100% correct now.

Csaba

Former Member
0 Kudos

So very briefly: craft a PrintReportOptions, set the PrinterName there an pass it to _reportDocument.ReportClientDocument.PrintOutputController.PrintReport(printReportOptions);

and not just null like http://scn.sap.com/docs/DOC-6391 suggests.

0 Kudos

10.2 is completely different than the kbase article you referenced and CR for VS is completely deifferent than the kbase also.

You can use the PrintToPrinter API as noted in the attached sample app.

Former Member
0 Kudos

Hi Don,

I tried that signature version of PrintToPrinter, but it doesn't help. I set up the .NET native PrinterSettings and PageSettings, but seemingly it grabs the PrinterName from the report document's (which I use to call the PrintToPrinter) PrintOptions. But the PrinterName in the PrintOptions cannot be set, and its an empty string. So whatever I set the PrinterName in the System.Drawing.Printing.PrinterSettings, it got ignored and overridden by the PrintOptions.

Once again: this problem arises only when the Report Document's "No Printer" checkbox is checked in the report designer. SO in this case the only way to print to any printer is the code I cited and found with exhaustive search of possible printing functions on various APIs:

_reportDocument.ReportClientDocument.PrintOutputController.PrintReport(printReportOptions); // where the printReportOptions has the wnated PrinterName set

I marked your answer helpful before for respect, and I still respect your help, but now I'll unmark it, because it didn't work for this particular problem, and I don't want to mislead anyone else who read this thread.

0 Kudos

Try this:

private void btnPrintToPrinter_Click(object sender, EventArgs e)
{
    System.Drawing.Printing.PrintDocument pDoc = new System.Drawing.Printing.PrintDocument();
    CrystalDecisions.Shared.PrintLayoutSettings PrintLayout = new CrystalDecisions.Shared.PrintLayoutSettings();
    System.Drawing.Printing.PrinterSettings printerSettings = new System.Drawing.Printing.PrinterSettings();

    printerSettings.PrinterName = cboCurrentPrinters.SelectedItem.ToString();

    // don't use this, use the new button
    //PrintLayout.Scaling = PrintLayoutSettings.PrintScaling.DoNotScale;

    System.Drawing.Printing.PageSettings pSettings = new System.Drawing.Printing.PageSettings(printerSettings);

    //rpt.PrintOptions.DissociatePageSizeAndPrinterPaperSize = false;
    rpt.PrintOptions.PrinterDuplex = PrinterDuplex.Simplex;

    System.Drawing.Printing.PageSettings pageSettings = new System.Drawing.Printing.PageSettings(printerSettings);

    if (pDoc.DefaultPageSettings.PaperSize.Height > pDoc.DefaultPageSettings.PaperSize.Width)
    {
        rpt.PrintOptions.DissociatePageSizeAndPrinterPaperSize = true;
        rptClientDoc.PrintOutputController.ModifyPaperOrientation(CrPaperOrientationEnum.crPaperOrientationPortrait);
    }
    else
    {
        rpt.PrintOptions.DissociatePageSizeAndPrinterPaperSize = true;
        rptClientDoc.PrintOutputController.ModifyPaperOrientation(CrPaperOrientationEnum.crPaperOrientationLandscape);
    }

    rpt.PrintToPrinter(printerSettings, pSettings, false, PrintLayout);

    MessageBox.Show(rpt.PrintOptions.PrinterName.ToString());
}

Don

Former Member
0 Kudos

Ok, I installed Crystal v13 SP5 SDK and now I got it working without using RAS API and following your instructions. In my case this boils down to this very simple code:

      CrystalDecisions.Shared.PrintLayoutSettings PrintLayout = new CrystalDecisions.Shared.PrintLayoutSettings();

      _reportDocument.PrintOptions.PrinterDuplex = PrinterDuplex.Simplex;

      _reportDocument.PrintOptions.DissociatePageSizeAndPrinterPaperSize = true;

      _reportDocument.PrintToPrinter(pPrinterSettings, pPageSettings, false, PrintLayout);

But note, that

MessageBox.Show(_reportDocument.PrintOptions.PrinterName.ToString());

will be still empty string indeed. But goes to the wanted printer now regardless.

It seems to be important, that we set the DissociatePageSizeAndPrinterPaperSize to true, and then pass false for the reformatReportPageSettings. I'm sure that I tried that combination when I permuting all possibilities. Can it happen that the SP5 made this work?

Anyways, I marked your answer as correct now, since my solution brought in the RAS API too. Now I can go with the .NET API only.

Former Member
0 Kudos

Just a note: it wasn't SP5 which solved the issue. It works with SP4 too.

Answers (3)

Answers (3)

rene_de_mare
Discoverer
0 Kudos

This page was very interesting as I ran into the same problem using CRforVS_13 components in a WPF application.

After reading several solutions I felt that the reason had to lie in the 'no printer' and 'Dissociate Page and Printer paper size' options that we also have set as std in our reports.

The reason for this is that if you don't set the 'optimize for screen' option, Crystal Reports often takes a sweet time (30sec+) to display or print the report when the report is run in a different environment than our own (which is always the case). Something to do with a wait for timeout while finding the original printer I guess...

The solution to the problem that CR ignores set printer and prints to the default printer instead turned out to be quite simple.

What worked for me was;

          '//_RptDoc is the CrystalDecisions.CrystalReports.Engine.ReportDocument loaded with the .rpt file

     _RptDoc.PrintOptions.NoPrinter = False   


     If pPrinterName.Length > 0 Then _

          _RptDoc.PrintOptions.PrinterName = pPrinterName


Perhaps you guys ran into a whole kind of different and more complicated problems but in our case CR doesn't ignore the new printer anymore if the NoPrinter property is set to False. We are using the CRforVS_13_0_16 (update 16) components.

0 Kudos

Interesting....

Curious, if you open the report in CR Designer and check on the option Dissociate.... does that work for you? No delay looking for the default printer.

Don

rene_de_mare
Discoverer
0 Kudos

Don, we never have delays opening a report in house but we noticed this behaviour at clients using our software. This delay problem has been around since CR XI and we then solved it by setting the 'no printer' checkmark at the rpt page settings. And this indicates that the 'developer printer' is being looked for quite a long time before continuing with the default printer on the system.

I guess Csaba's company ran into the same problem some time ago hence the 'no printer' option policy for CR reports.

With our 'new' app that uses the CR2013 reports - with the always printing to default printer - problem all reports had the Dissociate option turned on and with the intended printer (HP Officejet 100 mobile bluetooth printer) selected during development of the reports. But when at the client's office a different printer was selected from within our software this was most of the time ignored by CR in exactly the way Csaba described. Thinking back to the delay problem we set the No printer option on hoping that that would allow the report to set a different printer but alas. Turning the Option NoPrinter off after loading the report and then change the printer does work (for us at least).

Turning the PrintOptions.DissociatePageSizeAndPrinterPaperSize property on or off did not make a difference.

0 Kudos

Hi Rene,

Yes in house would not show the problem for you since the printers are available obviously.

We did have this problem early in CR 2008 and we fixed it and it's not been a problem since but it is possible the WPF viewer never got that update.

I'll have to test using one of the reports from a customer that I do not have their printer.

Don

0 Kudos

Did a quick test here and I never saw any delay.

Can you attach your report with saved data so I can test it? Actually I don't think it needs saved data since the delay I believe is on loading the report.

Don

rene_de_mare
Discoverer
0 Kudos

Hi Don, if you say the delay problem has been solved in CR2008 and your tests prove you right I'm sure it is solved now. We were using CR11R2 for a long time then upgraded to CR2013 for this WPF project. In that project we did not set the NoPrinter option within the reports initially but disconnected Page and Printer Paper sizes (DissociatePageSizeAndPrinterPaperSize).

The reason I mentioned the NoPrinter option is because setting this property to False before changing the PrinterName made the CRforVS viewer print to the assigned printer. Without it the PrinterName assignment is ignored (traced it and the PrinterName stays blank resulting into outputting to the default printer).

I appreciate the attention to the delay problem but that is not the issue here (and probably already solved and if not I think the NoPrinter options is an acceptable solution). If you still want an example report I can send you this though.

Best regards,

René

Former Member
0 Kudos

We had the problem described here and in other threads where ReportDocument.PrintOptions.PrinterName and PrintToPrinter function stopped working after we upgraded to Crystal Reports 13.0.2 - we are now in Crystal Reports 13.0.7 and the bug is still there. It always prints to Windows Default Printer instead of selected printer (PrinterName stays blank).

Since SAP has stated that they will not fix the PrintToPrinter function and says to use ReportAppServer instead of ReportDocument then I made this code change. Following the information on this thread and other threads I have code that now prints to the correct printer. However, this works only for regular 8x10 paper printers. When printing to a zebra label printer the text comes out extremely tiny.

I know the driver settings are correct because if I print from Notepad, or using the old PrintToPrinter function it is the right size for a 3x2 label. When I print using PrintOutputController.PrintReport instead it outputs a tiny label. Below is the code I am using to go from ReportDocument to PrintOutputController. I commented out the PaperSize, PaperSource, and PrinterDuplex options but that did not fix the problem.

Dim rcd As CrystalDecisions.ReportAppServer.ClientDoc.ISCDReportClientDocument = report.ReportClientDocument

Dim poc As CrystalDecisions.ReportAppServer.Controllers.PrintOutputController = rcd.PrintOutputController

Dim printOptions As New CrystalDecisions.ReportAppServer.Controllers.PrintReportOptions()

printOptions.JobTitle = report.SummaryInfo.ReportTitle

'printOptions.PaperSize = report.PrintOptions.PaperSize

'printOptions.PaperSource = report.PrintOptions.PaperSource

'printOptions.PrinterDuplex = report.PrintOptions.PrinterDuplex

printOptions.NumberOfCopies = copies

printOptions.Collated = collate

If Not String.IsNullOrEmpty(printerName) Then

  printOptions.PrinterName = printerName

End If

'Finally, print it.

poc.PrintReport(printOptions)

By the way, if I print from the Preview dialog (CrystalDecisions.Windows.Forms.CrystalReportViewer) it behaves the same as the new print code above. In other words, CrystalReportViewer prints to the correct selected printer but it also prints very tiny text on the (USB) label printer. So my guess is that the code we did is correct and now we have the same bug as Crystal Report's own dialog.

0 Kudos

Try SP 9, it can get the saved printer name from the report so you can then add code to use the same name as well as the Custom Paper size.

You do need to use RAS and the PrintOutputController.

Use your own print button to handle this...

Don

0 Kudos

I know this works, I've spent a lot of time making sure it works without scaling.

Try this test app...

Former Member
0 Kudos

Don,

Thanks for the quick response. I have upgraded my computer to CR 13.0.9. However the zip file attached to your latest post just has a txt file with some junk content (binary data). Please post the sample code here or as text files.

Thank you.

Italo.

0 Kudos

Unzip the file and then rename the *.txt to *.zip then you can unzip the project.

This forum won't attach zip files so we ahve to rename them...

Don

Former Member
0 Kudos

Thank you. This is an impressive prototype. I just had to add an rpt file with 5 lines of text to simulate what gets printed to the label printer. Are there any options I should be using on the RASPrinter2010 GUI? I tried different settings and always got the same results using this test app:

If I print to regular network printer on 8x10 paper it looks good.

If I print to Zebra label printer (which prints 3in x 2in labels) using POController button the text comes out very tiny.

With our old code which uses PrintToPrinter it prints the label correctly, on the same computer and printer, but the downside is that it has to be the Windows Default Printer. Also notepad prints correctly. So this tells me the settings on the Zebra driver are correct. One weird thing related to the driver is in Printer Properties (in Windows) there is a checkbox that says "Always use driver settings". If this is checked the label prints with the correct orientation but text is still too small to read. If it is unchecked the text is sideways (and tiny) so that is worse.

I have been told to leave the "Always use driver settings" option checked because our customers want the application to print in the label dimensions, etc, specified by the printer. So what we really want is to just send the text/graphics to the printer and let the printer properties/preferences in Windows determine the paper size, orientation, margins, etc. I can send you a screen shot of the Zebra printing preferences dialog if that helps.

0 Kudos

Hi Italo,

That app is by far not complete and may ahve bugs in it or parts, you need to modify and "fix" any issues.

Work flow is open the report, in the top left area select the Zebra printer and choose the custom paper size you ahve selected. You can then use the Set Printer info button or use the POC or P2P button to print. But run in DEbug mode so you can see what the various printer properties are being used and/or set to.

Which Zebra print driver are you using? Please post a link so I can get it also.

I have a ZM200 Zebra printer and so does R&D so I'm sure this should work, unless Zebra or whomevers Printer driver you are using has altered something.

Don

Former Member
0 Kudos

Don,

My Zebra label printer is GK420t but it prints correctly if I use Notepad or old P2P code.

G-Series GK Desktop Printers

Here is what I figured out using your test application. If I open the RPT file and just click the POController button it works. However, if I click "View Report" first then POController button I get the tiny text which my software started doing when I switched from P2P to PrintOutputController.

So I think there is a bug in CrystalReportViewer and I must have the same bug in my code (or in my RPT file) even though I am not going through CrystalReportViewer to print. As far as I can tell my code is exactly the same code as your btnPOController_Click_1 method. The only difference is I get the ReportDocument as input from older VB.NET code.

Here is how ReportDocument is created:

Dim Report As New ReportDocument

        Report.Load(ReportNameValue, CrystalDecisions.Shared.OpenReportMethod.OpenReportByTempCopy)

'added the following to assure that the xRpt object was valid before moving on:

Application.DoEvents()

And then after setting all the options like margins, and loading the data from database, I call my new C# class which I wrote based on your prototype. Can I attach or email you my cs file?

Dim rp As New ReportPrinter(Report)

rp.Print(PrinterName, Copies, bolCollate)

Thanks.

Italo.

0 Kudos

Exactly.... POC uses RAS to print. POC uses framework to print and there is NO fix for that. We are not going to update the functionality of P2P. It is what it is due to legacy functionality, it's how CR Basic in VS 2003 -> 2008 use.

NOTEPAD uses native WIN32 API's, Microsoft themselves do not use the Framework in any of their major products, likely because they figure it doesn't work either... Word is still writen in native C++ so not valid test either.

Use POC to do the printing. P2P has a limitation of windows framework and system.printer functionality.

So no need to send me your app, it's not going to work.

I've included a sample app that shows how to change the CR export button and use your own code to put the POC function in there.

Or simply disable the CR viewers Print button and use your Print own.

Don

Former Member
0 Kudos

Don,

I AM USING PrintOutputController and it still prints with the wrong size/scale. The only reason I bring up CrystalReportViewer is because it behaves the same way. As far as I can tell my new C# class is the same code as your code that uses POC to print.

That is why I would like to send you my cs file so that you can tell me what I am missing.

Thanks.

Italo.

Former Member
0 Kudos

Okay I think I figured it out. No matter what I set in code, the paper size and orientation is what is set in the RPT file. This was not the case with P2P but is now the way it works with RAS/POC.

That is why, even though I used the same C# code from the test application on my new Print method, it still did not work. The difference was in the RPT files. So (bad news) I have to update hundreds of RPT files to set the size (Horizontal, Vertical) and Orientation. Also have to select "Dissociate Formatting Page Size and Printer Paper Size" on each RPT file.

Former Member
0 Kudos

I'm having exactly the same problem.

If the report has 'No Printer' set or the Default Printer is not the one we want to send a job to, our reports are coming out tiny and completely out of scale.

It seems that Crystal completely ignores whatever Printer we assign it to in VB.NET and has a mind of it's own. This is only happening since the v13 update and I'm on the current service pack (v13.0.6).

I've tried the code above but I'm not having any luck. You don't happen to have the full code, including all the System.Drawing.Printing.PrinterSettings and CrystalDecisions.ReportAppServer.Controllers.PrintReportOptions declarations, at all?

If anyone else has any advice I'd appreciate it

0 Kudos

Download the sample app I attached on

Former Member
0 Kudos

David,

Just look at my "

PrintToPrinter function that my pPrinterSettings parameter is aSystem.Drawing.Printing.PrinterSettings, and the pPageSettings parameter is a System.Drawing.Printing.PageSettings. _reportDocument is a CrystalDecisions.CrystalReports.Engine.ReportDocument implementing ICrystalReportDocument.

Set the desired printer name in the system's PrinterSettings parameter. As I mention, you won't get a feedback that the set was successful (_reportDocument.PrintOptions.PrinterName is empty after printing), but if you follow some tiny details, like DissociatePageSizeAndPrinterPaperSize, and parameters to the PrintToPrinter, it should work. You can try permutation of parameter variations.

Csaba

Former Member
0 Kudos

Csaba,

Thanks very much. I basically fixed my problem with a mixture of code and editing the report & changing the Page Setup in Crystal Reports 11. We were currently using XI R2 so I think this is partly where the issue lied.

Code:

Dim PrintLayout As New CrystalDecisions.Shared.PrintLayoutSettings

PrintLayout.Scaling = CrystalDecisions.Shared.PrintLayoutSettings.PrintScaling.Scale

Dim printerSettings As New System.Drawing.Printing.PrinterSettings()

printerSettings.PrinterName = printerName

Dim pageSettings As New System.Drawing.Printing.PageSettings(printerSettings)

CrystalReport.PrintOptions.PrinterName = printerName

CrystalReport.PrintOptions.DissociatePageSizeAndPrinterPaperSize = True

CrystalReport.PrintToPrinter(printerSettings, pageSettings, False, PrintLayout

I then set 'No Printer' and 'DissociatePageSizeAndPrinterPaperSize' both to True and then manually specified the page dimensions.

Former Member
0 Kudos

Good to hear!