S
shownl
Unregistered / Unconfirmed
GUEST, unregistred user!
我在win2000做一个打印监控的程序,但是在监控打印份数和张数时有时候正确有时候不正确总是少,不知道什么原因,小弟很着急,看有没有高高手解决这个问题???
麻烦各位看看!!!
我使用的源码如下:
procedure Tfrm_Main.MonitorFunc(APrinterName: string);
var
sTemp,sErrPos : string;
jobs : array [1..2000] of JOB_INFO_2;
//保留打印作业详细信息
size : DWORD;
jobs1 : array of JOB_INFO_2;
//动态数组用于对大于size的任务进行操作
pcbNeeded,dObject : DWORD;
//所有打印字节数
actNeed :integer;
pcReturned : DWORD;
//打印任务数
buf : Pchar;
//指向打印机或机器名
ret1:Bool ;
//获得打印机句柄返回值
ret:Bool ;
//获得打印机任务返回值
bMonitor:boolean;
//监控标志
len: integer ;
j : integer;
pPntDefRINTER_DEFAULTS ;
chgObject :THANDLE;
pdwChange WORD;
fcnreturn :BOOL;
hPrinter : THandle ;
//打印机句柄
ppPrinterNotifyInfo PrinterNotifyInfo;
pPrinterNotifyOptionsRINTER_NOTIFY_OPTIONS;
mntSite :TMonitorSite_Struct;
//监控现场结构
prnDetail : TPrintDetail_Struct;//打印明细结构
StdInfo : TStudentInfo_Struct;//学生信息结构
srtPrinter : TPrinters_Struct;//打印机设置结构
cTemp :do
uble;
begin
size := 2000*sizeof(JOB_INFO_2);
jobs1 := nil;
pcbNeeded := 0;
pcReturned := 0;
pPntDef.DesiredAccess := PRINTER_ALL_ACCESS;
buf:= StrAlloc(255*SizeOf(Char));
GetMem(ppPrinterNotifyInfo,SizeOf(TPrinterNotifyInfo));
len:=Length(APrinterName);
StrPLCopy(buf,Pchar(APrinterName),len);//................字符串到字符的转换,
ret1:= OpenPrinter(buf,hPrinter,@pPntDef);//................获得打印机句柄
if(not ret1) then
begin
MessageDlg('获取打印机句柄异常!',mtError,[mbOK],0);
exit;
end;
srtPrinter := dm_MonitorDM.GetPrinterStruct(APrinterName);
bMonitor := true;
chgObject := FindFirstPrinterChangeNotification(hPrinter,PRINTER_CHANGE_JOB, 0, @pPrinterNotifyOptions);// PRINTER_CHANGE_ALL
while bMonitordo
begin
do
bject:=WaitForSingleObject(chgObject, WAIT_TIMEOUT);
if(dObject = WAIT_TIMEOUT) then
begin
Application.ProcessMessages;
continue;
end;
fcnreturn := FindNextPrinterChangeNotification(chgObject, pdwChange, Pointer(@pPrinterNotifyOptions), Pointer(ppPrinterNotifyInfo));
if (fcnreturn) then
begin
if (pdwChange and PRINTER_CHANGE_ADD_JOB)>0 then
begin
ret:= EnumJobs(hPrinter, 0, 127, 2,nil, 0,pcbNeeded,pcReturned);
//必要的一步,先取出打印机里任务的字节数,然后决定jobs1变量大小。//--------------------------①
if (ret and (pcbNeeded>size)) then
//.................重定义Jobs1, 根据pcbNeeded决定使用哪个变量
begin
actNeed:=pcbNeeded;
GetMem(jobs1, actNeed*sizeof(JOB_INFO_2));
ret:= EnumJobs(hPrinter, 0, 127, 2,@jobs1, actNeed, pcbNeeded, pcReturned);
end else
ret:= EnumJobs(hPrinter,0,127, 2,@jobs,size, pcbNeeded, pcReturned);//-----------------------------③
if(not ret)then
begin
MessageDlg('打印服务器监控异常!',mtError,[mbOK],0);
end;
if(pcbNeeded<size) and (pcbNeeded>0)then
begin
for j:=1to pcReturneddo
begin
try
sTemp := String(jobs[j].pMachineName);
mntSite.sComputerID := dm_MonitorDM.GetPrintComputerName(Copy(sTemp,3,Length(sTemp)-2));
//计算机名称
StdInfo := dm_MonitorDM.GetStudentInfo(mntSite.sComputerID);
mntSite.iJobID := jobs[j].JobId;
//任务ID
mntSite.sStudentNo := StdInfo.sStudentNo;
//学号
mntSite.sName := StdInfo.sName;
//姓名
mntSite.dtPrintTime := Now;
//打印时间
mntSite.sDocName := copy(String(jobs[j].pDocument),1,49);
//打印文档名称
mntSite.sPaperType := Trim(srtPrinter.sPaperType);
//打印纸张类型
mntSite.iCopys := jobs[j].pDevMode.dmCopies;
//打印份数
mntSite.sPrinterName := String(jobs[j].pPrinterName);
//打印机名称
if (mntSite.iCopys>1)then
begin
mntSite.iTotalPages := jobs[j].TotalPages * mntSite.iCopys;
//打印页数
mntSite.iPagePrinted := jobs[j].PagesPrinted * mntSite.iCopys;
end else
begin
mntSite.iPagePrinted := jobs[j].PagesPrinted;
mntSite.iTotalPages := jobs[j].TotalPages;
end;
end;
麻烦各位看看!!!
我使用的源码如下:
procedure Tfrm_Main.MonitorFunc(APrinterName: string);
var
sTemp,sErrPos : string;
jobs : array [1..2000] of JOB_INFO_2;
//保留打印作业详细信息
size : DWORD;
jobs1 : array of JOB_INFO_2;
//动态数组用于对大于size的任务进行操作
pcbNeeded,dObject : DWORD;
//所有打印字节数
actNeed :integer;
pcReturned : DWORD;
//打印任务数
buf : Pchar;
//指向打印机或机器名
ret1:Bool ;
//获得打印机句柄返回值
ret:Bool ;
//获得打印机任务返回值
bMonitor:boolean;
//监控标志
len: integer ;
j : integer;
pPntDefRINTER_DEFAULTS ;
chgObject :THANDLE;
pdwChange WORD;
fcnreturn :BOOL;
hPrinter : THandle ;
//打印机句柄
ppPrinterNotifyInfo PrinterNotifyInfo;
pPrinterNotifyOptionsRINTER_NOTIFY_OPTIONS;
mntSite :TMonitorSite_Struct;
//监控现场结构
prnDetail : TPrintDetail_Struct;//打印明细结构
StdInfo : TStudentInfo_Struct;//学生信息结构
srtPrinter : TPrinters_Struct;//打印机设置结构
cTemp :do
uble;
begin
size := 2000*sizeof(JOB_INFO_2);
jobs1 := nil;
pcbNeeded := 0;
pcReturned := 0;
pPntDef.DesiredAccess := PRINTER_ALL_ACCESS;
buf:= StrAlloc(255*SizeOf(Char));
GetMem(ppPrinterNotifyInfo,SizeOf(TPrinterNotifyInfo));
len:=Length(APrinterName);
StrPLCopy(buf,Pchar(APrinterName),len);//................字符串到字符的转换,
ret1:= OpenPrinter(buf,hPrinter,@pPntDef);//................获得打印机句柄
if(not ret1) then
begin
MessageDlg('获取打印机句柄异常!',mtError,[mbOK],0);
exit;
end;
srtPrinter := dm_MonitorDM.GetPrinterStruct(APrinterName);
bMonitor := true;
chgObject := FindFirstPrinterChangeNotification(hPrinter,PRINTER_CHANGE_JOB, 0, @pPrinterNotifyOptions);// PRINTER_CHANGE_ALL
while bMonitordo
begin
do
bject:=WaitForSingleObject(chgObject, WAIT_TIMEOUT);
if(dObject = WAIT_TIMEOUT) then
begin
Application.ProcessMessages;
continue;
end;
fcnreturn := FindNextPrinterChangeNotification(chgObject, pdwChange, Pointer(@pPrinterNotifyOptions), Pointer(ppPrinterNotifyInfo));
if (fcnreturn) then
begin
if (pdwChange and PRINTER_CHANGE_ADD_JOB)>0 then
begin
ret:= EnumJobs(hPrinter, 0, 127, 2,nil, 0,pcbNeeded,pcReturned);
//必要的一步,先取出打印机里任务的字节数,然后决定jobs1变量大小。//--------------------------①
if (ret and (pcbNeeded>size)) then
//.................重定义Jobs1, 根据pcbNeeded决定使用哪个变量
begin
actNeed:=pcbNeeded;
GetMem(jobs1, actNeed*sizeof(JOB_INFO_2));
ret:= EnumJobs(hPrinter, 0, 127, 2,@jobs1, actNeed, pcbNeeded, pcReturned);
end else
ret:= EnumJobs(hPrinter,0,127, 2,@jobs,size, pcbNeeded, pcReturned);//-----------------------------③
if(not ret)then
begin
MessageDlg('打印服务器监控异常!',mtError,[mbOK],0);
end;
if(pcbNeeded<size) and (pcbNeeded>0)then
begin
for j:=1to pcReturneddo
begin
try
sTemp := String(jobs[j].pMachineName);
mntSite.sComputerID := dm_MonitorDM.GetPrintComputerName(Copy(sTemp,3,Length(sTemp)-2));
//计算机名称
StdInfo := dm_MonitorDM.GetStudentInfo(mntSite.sComputerID);
mntSite.iJobID := jobs[j].JobId;
//任务ID
mntSite.sStudentNo := StdInfo.sStudentNo;
//学号
mntSite.sName := StdInfo.sName;
//姓名
mntSite.dtPrintTime := Now;
//打印时间
mntSite.sDocName := copy(String(jobs[j].pDocument),1,49);
//打印文档名称
mntSite.sPaperType := Trim(srtPrinter.sPaperType);
//打印纸张类型
mntSite.iCopys := jobs[j].pDevMode.dmCopies;
//打印份数
mntSite.sPrinterName := String(jobs[j].pPrinterName);
//打印机名称
if (mntSite.iCopys>1)then
begin
mntSite.iTotalPages := jobs[j].TotalPages * mntSite.iCopys;
//打印页数
mntSite.iPagePrinted := jobs[j].PagesPrinted * mntSite.iCopys;
end else
begin
mntSite.iPagePrinted := jobs[j].PagesPrinted;
mntSite.iTotalPages := jobs[j].TotalPages;
end;
end;