Sunday, February 26, 2006

Adobe Acrobat 7.0 Browser Control Type Library (ActiveX or COM)

Update: Please check out the other PDF related links in the sidebar as well.

Some horrors are erased!! Gasp !!

I came across the Adobe Acrobat 7.0 Browser Control Type Library that could be used to display and print PDF files on desktop (Windows forms) applications [I haven't explored utilizing this in a webpage, so that will have to wait]. This is really good stuff for some people, for it is an ActiveX control that you could utilize to automate certain PDF-related actions, instead of relying on the AcroRd32.exe process commandline options or DDE messaging (or worse - Win32 programming).

However, every approach has it's pitfalls.
And someone's already had a problem -

Bah. I can't believe that Adobe hasn't stepped up to hand out a library that will print any PDF with all of the printer settings available to be changed. (You apparently can create an Interop around their Acrobat TypeLib, but its features are limited and it can only print to the default printer.)

Oh well, that's why folks can charge lots of money for libraries I guess.

And if you have funds, then take this advice from an ex-Adobe employee a bit seriously, for he says -

I can give ya a little info on this as a former Adobe Employee and specifically dealing with Acrobat. They do have a SDK that allows you to work with PDFs but its not free, it does work in both managed and unmanaged code and they give some good examples done in C# and but here again its not free. I would look to some of the free PDF stuff and that may work but this is workable if you have the SDK because you can actually create a PDF object and load in that PDF and then use c# to print it like you would anything else.

Here's the CodeProject article utilizing the Adobe Acrobat 7.0 ActiveX object for communicating with Acrobat Reader, along with the .Net example utilizing the Browser Type Library that is described in the comments.

Ok, want to know more about this library ? Hop on and download the Adobe Acrobat Inter-Application Communication (IAC) Reference from the Adobe site (pdf download). The Acrobat Browser Type Library is provided by the AxAcroPDFLib.AxAcroPDF object. This should be suitable for most of your needs. You can access it by adding a reference to AcroPDF.dll (that resides in the ActiveX directory under the Acrobat application directory) in your IDE environment.

Technical Notes
  • If you dont want to display the PDF document in a Windows Forms application, then you'll have to set the 'Visible' property to false. And if you want to send the PDF file directly to the printer, then you could use one of the methods provided by the control for that purpose - Print, PrintAll, PrintAllFit, PrintPages, PrintPagesFit. That should be suitable for your silent print needs in most cases.
  • You could experience problems when you have to print to the default printer. The default printer seem to be determined by Acrobat when it is loaded, and not by Windows. So changing the default printer mid-way through your application's runtime might cause unexpected behavior.
  • It is impossible to "name" / "determine" the printer that is used to print the document. Unless you don't want the user to access all the printer settings that could change the workflow, the only solution is to use the PrintWithDialog method (which is used to present the Acrobat Print Dialog Box that allows the user to make changes to the number of copies to be printed, or print to a file).

And to help people searching for solutions to common problems involving Adobe Acrobat (even Reader), I'm posting a link to Experts Exchange's set of time-tested Adobe Acrobat solutions.

Sunday, February 19, 2006

Internet based silent print using scripting languages (client side scripting). Why doesnt it work?

Update: Please do not forget to check the other PDF related links in the sidebar

You want to allow your site visitors or customers to print documents without popping up a dialog box. You dont want to display a print dialog box because you feel it's a distraction or a devaition from normal website browsing flow. You're probably right in asking for a silent print feature in the browser object model, especially in the model provided by JavaScript (or any client side scripting language).

In this short article (that would be extended later on, depending on how many people read it and find it useful), I will detail why the browser model doesnt allow for silent printing , or automatic printing over an Internet-based website, with minimum or no user interaction.

Let's get into the details . . . . .

Basically, the job of the browser is to display webpages. Technically, this means that the browser is supposed to do only certain types of jobs - display HTML and allow for user-interaction with dynamic elements in the webpage. The browser is not allowed to do certain things by default - execute a snippet of code, download files that it doesnt understand or recognize, create system files that would execute in the background and log user activity.

You could extend the browser through plugins to do some of those jobs. You could write scripts in client-side scripting languages to perform "certain" tasks at the client's computer. But client side scripting languages would have limitations on what a scripter is able to command the client's browser to do.

That's purely because of the nature of the Internet - it's not a trusted zone.
What's a trusted zone ?
Well, basically it is a place where all the accessible resources are trusted by your computer (indirectly, you trust the resources at the place). It could be the local area network (so long as you're sure that your computer will be secure in it), or the network of your business associate or subsidary (as long as you chose to trust the resources availble on the foreign network).

So what's the thing with trusted zones and untrusted zones ?
Trusted zones as the name says are places trusted by the client. The resources in such a place are capable of interacting with the resources at the client's place. The degree of such interaction depends totally on the nature and degree of the trust. For example, you trust that executables residing on your own drive/computer are far more trustworthy than the ones you downloaded off .

How does this affect automatic printing ? Or, why should this concern me ?
Code running in trusted environments have far more privileges than code running from an untrusted source. For example, executables in your computer are capable of deleting certain files from the hard disk, but code running in the browser will not be capable of doing so (until the user has granted that privilege). Printing, or better, automated printing requires that the end-user grant privileges to your code to access his/her printer (that's the user's printer not yours). The remote printer is a resource that belongs to the remote computer to which it is plugged into (even though, your office may have paid for it). To access the remote printer, it is required that the remote computer grant privileges to your code to access the remote printer.

Hell, I dont need privileges to access the remote printer. My boss says that the client trusts our website so the client should be able to print without any user interaction . Why I should believe you ?
There are websites out there that are capable of ruining your client's computer, so why not yours ? Is there anything special about your site ? And how does the client know that you are not using his printer to print advertisements (of no value to him) ?
And what is with the minimum user-interaction ? How are you so sure that the printer will always print the correct output ? What if something went wrong during printing ? Why does your client have a problem clicking a button in the print dialog box ?
The print dialog is there to -
  • grant access to your instructions to issue a print command,
  • allow the user to modify any necessary settings that are necessary for obtaining a successful printout.

I know of an environment where you're wrong !!
It's probably on ActiveX based websites. Nothing new there. ActiveX is known to be insecure, and is supported only on MS Internet Explorer. Dont be surprised if half of your users wont be able to access your website.
If you're talking about Java(not JavaScript), then again there is nothing new there. If you are able to produce a signed applet, then it is possible to automate the print process as much as possible. It's mileage depends on what libraries you are using, that is, how powerful the libraries are in their ability to access the printer options, and produce a clean printout with most of the settings provided by the programmer (that is, you) , and hence result in lesser user-interaction (because most of the settings are provided by the programmer).
There is also a possibility of Winforms applications being able to print over the Internet. Like the first option mentioned above, Winforms applications seems to work only on Microsoft Internet Explorer. Unlike ActiveX, Winforms applications written using the .Net framework are far more secure. The programmer can request for further privileges to be granted to the code during it's execution. So, if your program wants to access the printer, it must merely request for the necessary privileges. Of course, the user executing the program has to grant the privileges. But this is far better than having a code "lockout" - your code is unable to run because it cannot even request for such privileges; your client will have to explicitly make changes to his computer's configuration to allow it run.

What now?
Silent printing may be the tip of the iceberg. There are far more things that may not be possible using client side scripting languages. Most of them are not even things that should be solved using client side scripting. It's more an issue of whether people have analysed the business problem at hand, and have recognized that a browser based solution may not be the answer. Chances are that poorly architected and poorly designed solutions often call the limits of Javascript (and other scripting languages) into question. In most cases, the solution might be a Windows forms solution (or a background service or a cron job or . . . . . ), or sometimes a change in the business process (hah!).