在下正在作一个打印程序,我无从着手。有一设想:
    BitBtn1: TBitBtn;
    Label1: TLabel;
    Image1: TImage;
    Button1: TButton;
   ......
  private
    procedure poOutText(var X3, Y3, iCount: integer; ImageWrite: TBitmap; pricecount: real);
 ...............
  Image1.Canvas.Draw(0, 0, ImageWrite);    //调用函数画表头
............
 with   ImageWrite.Canvas do
  begin
     for i := 0 to 7 do
     begin
 ........
反正我这表就是表在Image1里面,然后就要打印image1里面的内容。用A4纸。现在我无从着手。要怎么开始设计,因为我没有测试条件,一切很茫然,各位高手经历知道的了,我这种感觉很烦。请各位帮助我了,最好加我的QQ:52258388
我愿意再给100分,只好带着我走过打印这道坎!!!!!!!

解决方案 »

  1.   

    用QR,FR或者RAVE实现吧.用第三方控件,提高你的效率.
      

  2.   

    是这样子的,控件的使用容易出问题,我怕万一,因为这个东西是做给一人哥们的公安系统用,我可能明年就出门了,所以不想用。功能简单点都无所谓,反正尽量不使用打印控件了。我的报表基本上完成了,就是不知道打印的方法。兄弟苦呀!!
    另问:我用Canvas的MOVE TO呀什么的,自己画的表格,算不算报表?哪玩意我画完了。请大虾们帮忙咯!!!!!!!!
      QQ:52258388。
      

  3.   

    當然可以了,在image上劃,只能操作Canvas,然後用Canvas的打印即可,用Canvas的LINE TO,MOVE TO
    查出數據用TEXT.OUT輸出數據在指定位置上也很方便,看看書很方便
      

  4.   

    UP者有分并且:请问如何在我的程序中得到A4与B5纸。以级相关的设置。
    A4怎么反映在Image1.cavas 上面。等等,请朋友们帮我呀!
      

  5.   

    现我有看有关的TPrinters的资料。大体有一点点感觉,但是期待DDJJ们帮助呀!!!现思路是:得到打印机的分辨率。
              然后根据地个分辨率,如:300*300,则像在Image里面用Canvas一样,利用prints的Canvas的画布将其画出来,然后beginDoc,但是请问的是:具体过程能不能提醒一下?
    我的QQ:52258388
    E-mail: [email protected]
      

  6.   

    with printer do
    begin
       begindoc;
       Canvas.StretchDraw(Rect(0, 0, Printer.PageWidth,  Printer.PageHeight),tmpImg.Graphic);
       enddoc;end;
      

  7.   

    找一本开发人员指南D2~D7的都行,里面的TPrinters介绍得比较详细
      

  8.   

    我有D5的指南的,不错。我看的Tprinters就是在里面看的。但是我基础不好,所以有些地方不懂。我想请教:
        一、用GetdeviceCaps得到X、Y的像素值以后。再用TRect来画,Cavas里面作的画是不是原样输出?
       二、纸张的大小设置问题。如:A4、横向打印。得到打印的分辨率以后,怎么做才能打出A4的大小?(有没有源码呀!!哥哥些!!)
      

  9.   

    你首先要搞清楚设备单位根逻辑单位的区别。在大多数的GDI函数中使用的是逻辑单位,它可以根据你的设置是毫米、厘米或者默认为像素。设备单位就是设备能够表现的最小长度单位,对于屏幕来说就是像素。在一英寸的逻辑单位中包含的设备单位的数量就是分辨率,单位dpi。你用GetDeviceCaps取得的就是这个东西。在Bitmap或者Image上面画图一般来说只是使用了屏幕的分辨率,在等比例放到打印纸上时,往往会出现锯齿(尤其是文本以及缩小了的图案)。所以你最好把报表画到一个元文件(TMetafile)上,然后再把该元文件画到打印机的画布上(可以直接StretchDraw上去),这时打印出来的字符什么的就不会出现锯齿。元文件的使用有别于TBitmap,看看帮助也就行了。同时要注意的是最好选择TrueType矢量字体。Arial是常用的矢量字体,而程序常用的默认值是MS Sans Serif,它是一个标量字体,在打印的时候不要使用它。进行打印的时候,你先取得在屏幕分辨率下对应的A4纸张的大小(这个用dpi换算一下就出来了)。然后以此为基准绘制你的图形(其实分页的逻辑才是难点和麻烦所在,不过在此不讨论)。把所有的图形绘制完成后,调用Printer的Canvas对象的StretchDraw方法把元文件绘制到打印机上就行了(当然你要参考Printer的PageWidth和PageHeight)。先这么多,不行的话再说吧……
      

  10.   

    有一点重要的补充,设置元文件的大小的时候用的是屏幕分辨率下的A4纸张的像素大小。
    算法如下:先取得打印机(分母)和屏幕的分辨率(分子)的比值,然后用此比值乘以打印机的PageWidth和PageHeight就得到了屏幕分辨率下的当前打印纸张大小。如果不设置元文件的大小,那么你在StretchDraw的时候可能会得不到正确的结果。
      

  11.   

    换算怎么换呀?你先取得在屏幕分辨率下对应的A4纸张的大小(这个用dpi换算一下就出来了。
    能给我一个大概的源程序吗?
      

  12.   

    metafile_dpix := GetDeviceCaps(MyMetafileCanvas.Handle, LOGPIXELSX);
    或者metafile_dpix := GetDeviceCaps(Form.Canvas.Handle, LOGPIXELSX);
    //因为一般说来元文件是以屏幕分辨率创建的,所以你也可以直接从屏幕获取数据printer_dpix := GetDeviceCaps(Printer.Handle, LOGPIXELSX);
    metafile.width := (Printer.PageWidth * metafile_dpix) / printer_dpix;
      

  13.   

    呵呵,没问题!var
      metafile_dpix, metafile_dpiy, printer_dpix, printer_dpiy;
      mf : TMetafile;
      mc : TMetafileCanvas;
      w, h : Integer;
    begin
      metafile_dpix := GetDeviceCaps(Form.Canvas.Handle, LOGPIXELSX);
      printer_dpix := GetDeviceCaps(Printer.Handle, LOGPIXELSX);
      metafile_dpiy := GetDeviceCaps(Form.Canvas.Handle, LOGPIXELSY);
      printer_dpiy := GetDeviceCaps(Printer.Handle, LOGPIXELSY);  mf := TMetafile.Create;
      try
        mf.Width := (Printer.PageWidth * metafile_dpix) / printer_dpix;
        mf.Height := (Printer.PageHeight * metafile_dpiy) / printer_dpiy;
        mc := TMetafileCanvas.Create(mf, 0);
        try
          w := Round(10{厘米} * metafile_dpix / 2.54{英寸/厘米});
          h := Round(15{厘米} * metafile_dpiy / 2.54{英寸/厘米});
          mc.MoveTo(0, 0);
          mc.LineTo(0, h);
          mc.LineTo(w, h);
          mc.LineTo(w, 0);
          mc.LineTo(0, 0);
        finally
          mc.Free;
        end;    Printer.BeginDoc;
        Printer.NewPage;
        Printer.StretchDraw(Rect(0, 0, Printer.PageWidth, Printer.PageHeight), mf)
        Printer.EndDoc;  finally
        mf.Free;
      end;
    end;上面的代码画出一个宽10厘米,高15厘米的矩形。同样的功能也可以用Rectangle来画。使用元文件并不是必要的,但是能给你带来莫大的好处。你可以在没有打印机的情况下调试你的程序,只需要加上一段显示元文件的代码就行了。
      

  14.   

    一个小错:
    Printer.StretchDraw(Rect(0, 0, Printer.PageWidth, Printer.PageHeight), mf)
    应该是
    Printer.Canvas.StretchDraw(Rect(0, 0, Printer.PageWidth, Printer.PageHeight), mf);代码没有测试过。不过应该没问题。
      

  15.   

    真是太谢谢你了,你所说的无打印情况下的测试代码你能给出来吗?
        mf.Width := (Printer.PageWidth * metafile_dpix) / printer_dpix;
        mf.Height := (Printer.PageHeight * metafile_dpiy) / printer_dpiy;
    以上两行代码是不是给出了元文件的总的宽和高。也就是将纸张的实际大小与元文件metafile相联系起来。wf.width与mf.height分别是纸的实际大小。对吗?(迷茫中!!)      mc := TMetafileCanvas.Create(mf, 0); //??
      w := Round(10{厘米} * metafile_dpix / 2.54{英寸/厘米});
      h := Round(15{厘米} * metafile_dpiy / 2.54{英寸/厘米});以上是绘制宽和高的了。2.54是代表了A4与实际大小的转换,但是你能详细讲一下他们的换算关系吗?从屏幕分辨率---打印机分辨率---到无文件----实际的绘图大小。我的天!!谢谢了。十分感谢!!!
      

  16.   

    打印机的300dpi是指在打印机的逻辑里,一英寸包含了300个点。
    屏幕通常为96dpi是指在屏幕上,一英寸包含了96个点。
    显然打印机打出来的图像要比屏幕细腻。你要在打印机上绘制长一英寸的线段,那么坐标长度就应该是300个点。
    你要在屏幕上绘制长一英寸的线段,那么坐标长度就应该是96个点。
    因为默认的情况下,元文件跟屏幕分辨率相同。所以你绘制了一条长为96个点的线段后,再StretchDraw到打印机上,因为自动缩放的缘故,在打印机上也会看到长1英寸的线段。顺便说一说,因为最后是使用StretchDraw,元文件不一定要按照96dpi的分辨率来绘制。在这里只是为了方便预览方便而已。所谓的“没有打印机的情况下调试你的程序”是指你可以通过显示元文件来观察打印成果。因为元文件是矢量图形,所以可以随便缩放而不会产生点阵图片缩放时产生的锯齿效应。不过要注意的是,元文件缩小显示时有可能出现缺线(尤其是横线和竖线)的现象,不要担心,打印时是没有问题的。而且要注意,打印时最好要采用TrueType字体(如Arial, Times New Rome等),否则可能会显示不正常。
      

  17.   

    对不起,因为我一般都不在网上,所以都不用QQ什么的。有事情就给我写Email吧。
    [email protected]