首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > .NET > C# >

用API打印有关问题:为什么只能打选取的.txt文件,不能打word,excel,html等,小弟我是向打印机输出byte[]

2012-01-16 
用API打印问题:为什么只能打选取的.txt文件,不能打word,excel,html等,我是向打印机输出byte[]啊选取.txt文

用API打印问题:为什么只能打选取的.txt文件,不能打word,excel,html等,我是向打印机输出byte[]啊
选取.txt文本文件打没有问题,但是选取word等文件打出来得就是乱码!!我是向打印机输出byte[]啊。。为什么。。

请高手指点。


using System;
using System.IO;
using System.Drawing.Printing;
using System.Runtime.InteropServices;

namespace XXL.Tools
{

  public class PrintingUtil
  {

  [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
  struct DOCINFOW
  {
  [MarshalAs(UnmanagedType.LPWStr)]
  public string pDocName;
  [MarshalAs(UnmanagedType.LPWStr)]
  public string pOutputFile;
  [MarshalAs(UnmanagedType.LPWStr)]
  public string pDataType;
  }

  [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = false,
  CallingConvention = CallingConvention.StdCall)]
  public static extern long OpenPrinter(string pPrinterName, ref IntPtr phPrinter, int pDefault);

  //[DllImport("winspool.Drv", EntryPoint = "OpenPrinterW",
  // CharSet = CharSet.Unicode, SetLastError = true,
  // ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  //static extern bool OpenPrinter(string src, ref IntPtr hPrinter, long pd);

  [DllImport("winspool.Drv", EntryPoint = "ClosePrinter",
  CharSet = CharSet.Unicode, SetLastError = true,
  ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  static extern bool ClosePrinter(IntPtr hPrinter);

  [DllImport("winspool.Drv", EntryPoint = "StartDocPrinterW",
  CharSet = CharSet.Unicode, SetLastError = true,
  ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  static extern bool StartDocPrinter(IntPtr hPrinter,
  int level, ref DOCINFOW pDI);

  [DllImport("winspool.Drv", EntryPoint = "EndDocPrinter",
  CharSet = CharSet.Unicode, SetLastError = true,
  ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  static extern bool EndDocPrinter(IntPtr hPrinter);

  [DllImport("winspool.Drv", EntryPoint = "StartPagePrinter",
  CharSet = CharSet.Unicode, SetLastError = true,
  ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  static extern bool StartPagePrinter(IntPtr hPrinter);

  [DllImport("winspool.Drv", EntryPoint = "EndPagePrinter",
  CharSet = CharSet.Unicode, SetLastError = true,
  ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  static extern bool EndPagePrinter(IntPtr hPrinter);

  [DllImport("winspool.Drv", EntryPoint = "WritePrinter",
  CharSet = CharSet.Unicode, SetLastError = true,
  ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
  static extern bool WritePrinter(IntPtr hPrinter,
  IntPtr pBytes, int dwCount, ref int dwWritten);


  //SendBytesToPrinter()
  //When the function is given a printer name and an unmanaged array of
  //bytes, the function sends those bytes to the print queue.
  //Returns True on success or False on failure.
  public bool SendBytesToPrinter(string szPrinterName,
  IntPtr pBytes, int dwCount)


  {
  // The printer handle.
  IntPtr hPrinter = new IntPtr(0);
  // Last error - in case there was trouble.
  int dwError;
  // Describes your document (name, port, data type).
  DOCINFOW di = new DOCINFOW();
  // The number of bytes written by WritePrinter().
  int dwWritten = 0;
  // Your success code.
  bool bSuccess;

  // Set up the DOCINFO structure.
  di.pDocName = "My C# .NET RAW Document";
  di.pDataType = "RAW";
  // Assume failure unless you specifically succeed.
  bSuccess = false;
  if (Convert.ToBoolean( OpenPrinter(szPrinterName, ref hPrinter, 0) ))//modified by XXL
  {
  if (StartDocPrinter(hPrinter, 1, ref di))
  {
  if (StartPagePrinter(hPrinter))
  {
  // Write your printer-specific bytes to the printer.
  bSuccess = WritePrinter(hPrinter, pBytes,
  dwCount, ref dwWritten);
  EndPagePrinter(hPrinter);
  }
  EndDocPrinter(hPrinter);
  }
  ClosePrinter(hPrinter);
  }
  // If you did not succeed, GetLastError may give more information
  // about why not.
  if (bSuccess == false)
  {
  dwError = Marshal.GetLastWin32Error();
  }
  return bSuccess;
  }



  public bool SendFileToPrinter(string szPrinterName, string szFileName)
  {
  // Open the file.
  FileStream fs = new FileStream(szFileName, FileMode.Open);
  // Create a BinaryReader on the file.
  BinaryReader br = new BinaryReader(fs);
  // Dim an array of bytes large enough to hold the file's contents.
  byte[] bytes = new byte[fs.Length];
  bool bSuccess;
  // Your unmanaged pointer
  IntPtr pUnmanagedBytes;

  // Read the contents of the file into the array.
  bytes = br.ReadBytes(Convert.ToInt32(fs.Length));
  // Allocate some unmanaged memory for those bytes.
  pUnmanagedBytes = Marshal.AllocCoTaskMem(Convert.ToInt32(fs.Length));
  // Copy the managed byte array into the unmanaged array.
  Marshal.Copy(bytes, 0, pUnmanagedBytes, Convert.ToInt32(fs.Length));
  // Send the unmanaged bytes to the printer.
  bSuccess = SendBytesToPrinter(szPrinterName,
  pUnmanagedBytes, Convert.ToInt32(fs.Length));
  // Free the unmanaged memory that you allocated earlier.
  Marshal.FreeCoTaskMem(pUnmanagedBytes);

  br.Close();//by XXL
  fs.Close();//by XXL

  return bSuccess;
  }


  public bool SendStringToPrinter(string szPrinterName, string szString)
  {
  bool bSuccess;
  IntPtr pBytes = new IntPtr(0);
  int dwCount;
  //How many characters are in the string?
  dwCount = szString.Length;
  //Assume that the printer is expecting ANSI text, and then convert


  //the string to ANSI text.
  pBytes = Marshal.StringToCoTaskMemAnsi(szString);
  //Send the converted ANSI string to the printer.
  bSuccess = SendBytesToPrinter(szPrinterName, pBytes, dwCount);

  Marshal.FreeCoTaskMem(pBytes);
  return bSuccess;
  }
  }
}

[解决办法]
你调用API打印出的效果 就是记事本显示的效果。你BYTE[] 得到的 BYTE 不是文本信息 里面有WORD文件头 和WORD的文件信息,打印出来就看不明白了。
[解决办法]
WORD的文件中有大量的控制字符,当然不一样啦

热点排行