我用下面的代码设置打印机的默认纸张的时候在执行CopyMemory 的时候,有的机器上可以成功,但更多的机器上出现"内存不能为read",更奇怪的是我在计算机A上设置打印机P1可以成功,但设置P2出错,在开发程序的计算机上设置P1和P2都没问题.请高手帮忙
Private Const CCHDEVICENAME = 32
Private Const CCHFORMNAME = 32
Private Type DEVMODE
dmDeviceName As String * CCHDEVICENAME
dmSpecVersion As Integer
dmDriverVersion As Integer
dmSize As Integer
dmDriverExtra As Integer
dmFields As Long
dmOrientation As Integer
dmPaperSize As Integer
dmPaperLength As Integer
dmPaperWidth As Integer
dmScale As Integer
dmCopies As Integer
dmDefaultSource As Integer
dmPrintQuality As Integer
dmColor As Integer
dmDuplex As Integer
dmYResolution As Integer
dmTTOption As Integer
dmCollate As Integer
dmFormName As String * CCHFORMNAME
dmUnusedPadding As Integer
dmBitsPerPel As Long
dmPelsWidth As Long
dmPelsHeight As Long
dmDisplayFlags As Long
dmDisplayFrequency As Long
End TypePrivate Type PRINTER_DEFAULTS
pDatatype As String
pDevMode As DEVMODE
DesiredAccess As Long
End TypePrivate Declare Function OpenPrinter Lib "winspool.drv" Alias "OpenPrinterA" (ByVal pPrinterName As String, phPrinter As Long, pDefault As PRINTER_DEFAULTS) As Long
Private Declare Function GetPrinter Lib "winspool.drv" Alias "GetPrinterA" (ByVal hPrinter As Long, ByVal Level As Long, buffer As Any, ByVal pbSize As Long, pbSizeNeeded As Long) As Long
Private Declare Function ClosePrinter Lib "winspool.drv" (ByVal hPrinter As Long) As Long
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As Long)
Private Declare Function SetPrinter Lib "winspool.drv" Alias "SetPrinterA" (ByVal hPrinter As Long, ByVal Level As Long, pPrinter As Any, ByVal Command As Long) As Long
Public Sub SetPrintDefault(ByVal FormName As String, PaperSize As Integer)
    Dim SizeNeeded As Long, buffer() As Long
    Dim pDef As PRINTER_DEFAULTS
    Dim X As DEVMODE
    Dim lret As Long
    Dim mhPrinter As Long
    Dim str As String
    
    pDef.DesiredAccess = PRINTER_ALL_ACCESS
    lret = OpenPrinter(Printer.DeviceName, mhPrinter, pDef)
    
    ReDim Preserve buffer(0 To 0)
    
    lret = GetPrinter(mhPrinter, 9, buffer(0), 0, SizeNeeded)
    
    ReDim Preserve buffer(0 To (SizeNeeded / 4) + 3) As Long
    
    lret = GetPrinter(mhPrinter, 9, buffer(0), UBound(buffer) * 4, SizeNeeded)
   
'*******************************************    CopyMemory X, ByVal buffer(0), Len(X)'*******************************************
    X.dmFields = &H10000 Or 2
    X.dmFormName = FormName & vbNullChar
    X.dmPaperSize = PaperSize
    CopyMemory ByVal buffer(0), X, Len(X)
    
    lret = SetPrinter(mhPrinter, 9, buffer(0), 0)
    
    ClosePrinter mhPrinterEnd Sub

解决方案 »

  1.   

    建议用VC来实现,VC底层控制较好。
      

  2.   

    将 *******************************************    CopyMemory X, ByVal buffer(0), Len(X)'*******************************************改成:
    dim yy as long
    yy=varPtr(x)
    CopyMemory yy, buffer(0), Len(X)也可能是打印机驱动程序的事或者你可以重装打印机改革端口是以下。
    可能是那块内存不能被read,但换个端口号可能行,以前我也遇到过
    类似问题,改个端口号就行了。