View Full Version : نحوه چاپ یک Panel
hadisalahi2
جمعه 20 آذر 1388, 19:55 عصر
با سلام.
چطور میتونم یک panel رو با کنترلهای داخل اون چاپ کنم؟
این پنل داخل یک فرمه.
فقط میخوام پنل چاپ بشه نه کل فرم.
Felony
جمعه 20 آذر 1388, 20:01 عصر
خیلی وقت پیش این کد رو نوشته بودم ، کلی گشتم تا براتون گیرش آوردم :
Uses Jpeg;
procedure SaveControlImageToFile(AControl:TWinControl;AFileN ame: StringUseJpegFormat:Boolean=True);
Var
Canvas : TCanvas;
Bmp : TBitmap;
Jpg : TJpegImage ;
Begin
try
Canvas := TCanvas.Create;
Canvas.Handle := GetDc(AControl.Handle);
Bmp := TBitmap.Create;
Bmp.Width := AControl.Width;
Bmp.Height := AControl.Height;
bmp.PixelFormat :=pf24bit;
Bmp.Canvas.CopyRect(Canvas.ClipRect, Canvas, Canvas.ClipRect);
if UseJpegFormat then
begin
Jpg := TJpegImage.Create;
jpg.PixelFormat := jf24bit;
Jpg.Assign(Bmp);
Jpg.SaveToFile(ChangeFileExt(AFileName,'.jpg'));
end
Else
Bmp.SaveToFile(ChangeFileExt(AFileName,'.bmp'));
finally
ReleaseDC(AControl.Handle, Canvas.Handle);
FreeAndNil(Bmp);
if UseJpegFormat then
FreeAndNil(Jpg);
FreeAndNil(Canvas);
end;
end;
نحوه ی استفاده :
SaveControlImageToFile(Panel1,'D:\a.jpg',True);
Felony
جمعه 20 آذر 1388, 20:16 عصر
یادم رفت بگم این کد از کنترل مورد نظر عکس میگیره و در یک فایل ذخیره میکنه ، میتونید برای پرینت گرفتن خودتون تغییرش بدید .
hadisalahi2
شنبه 21 آذر 1388, 08:22 صبح
با تشکر میشه ، زحمت اون قسمتش رو هم بکشید.
خیلی ممنون میشم.
یا علی
hadisalahi2
شنبه 21 آذر 1388, 09:04 صبح
در ضمن این خط
procedure SaveControlImageToFile(AControl:TWinControl;AFileN ame: StringUseJpegFormat:Boolean=True);
باید به خط زیر تغییر پیدا کنه:
procedure SaveControlImageToFile(AControl:TWinControl;AFileN ame:String;UseJpegFormat:Boolean=True);
hadisalahi2
شنبه 21 آذر 1388, 09:32 صبح
در ضمن چرا کل Panel رو در داخل فایل Jpeg ذخیره نمیکنه؟
در صورتی که بر روی پانل منوی یا کنترلی قرار داشته باشد که خارج از پنل باشد، باعث می شود که همان قسمتهای پنل در عکس ذخیره نگردند.
Felony
شنبه 21 آذر 1388, 13:58 عصر
برای پرینت گرفتن تغییرش دادم ، فقط باید یونیت Printers رو تو برنامتون Uses کنید :
procedure SaveControlImageToFile(AControl:TWinControl);
Var
Canvas : TCanvas;
Pri : TPrinter;
Begin
try
Canvas:=TCanvas.Create;
Pri:=TPrinter.Create;
Canvas.Handle := GetDc(AControl.Handle);
Pri.BeginDoc;
Pri.Canvas.CopyRect(Canvas.ClipRect,Canvas,Canvas. ClipRect );
Pri.EndDoc;
finally
ReleaseDC(AControl.Handle,Canvas.Handle);
Pri.Free;
end;
end;
hadisalahi2
شنبه 21 آذر 1388, 17:16 عصر
به این خط که میرسه خطای ACcess Validation میده.
Pri.BeginDoc;
در ضمن چرا هنگامی که پنل رو داخل داخل فایل Jpeg ذخیره میکنم تمام موضوعات داخل فایل ذخیره نمی شوند و قسمت پایین اون در فایل ذخیره نمیشه؟
Felony
شنبه 21 آذر 1388, 17:53 عصر
به این خط که میرسه خطای ACcess Validation میده.
Pri.BeginDoc;
در ضمن چرا هنگامی که پنل رو داخل داخل فایل Jpeg ذخیره میکنم تمام موضوعات داخل فایل ذخیره نمی شوند و قسمت پایین اون در فایل ذخیره نمیشه؟
احتمالا مشکل ازجای دیگه ای هست ، برای من که درست جواب داد ...
در مورد ذخیره ی عکس هم درست عمل میکنه ، عکس زیر یک نمونه که با همون کد گرفتم .
http://barnamenevis.org/forum/attachment.php?attachmentid=41109&stc=1&d=1260584443
hadisalahi2
شنبه 21 آذر 1388, 18:09 عصر
من کنترلهای داخل پنل رو به صورت RunTime ایجاد میکنم نه در حالت Design.
این قضیه میتونه باعث ایجاد خطا بشه؟
hadisalahi2
شنبه 21 آذر 1388, 18:29 عصر
متوجه مشکل اینکه چرا به صورت نصفه در پانل ذخیره میکه شدم.
علتش اینه که اگر هنگام ذخیره پانل در عکس اگر روی پانل کنترلی قرار داشته باشه اون رو هم در تصویر نهایی ذخیره میکنه.
در ضمن برای پرینت ، در یک پروژه جداگانه تست کردم ولی بازهم در همون خط پیغام خطا میده.
Felony
شنبه 21 آذر 1388, 20:28 عصر
در ضمن برای پرینت ، در یک پروژه جداگانه تست کردم ولی بازهم در همون خط پیغام خطا میده.
هر چی هست مشکل از کد نیست ، درایور پرینترتون مشکلی نداره ؟
hadisalahi2
شنبه 21 آذر 1388, 20:52 عصر
نه درایور رو هم دوباره نصب کردم.
از داخل بقیه نرم افزارها بدون هیچ مشکلی پرینت میگیره ولی از داخل دلفی پیغام خطا میده.
توی یک پروژه ساده هم امتحان کردم بازهم خطا میده.
در مورد ذخیره عکس روش بهتری سرغ ندارید؟
Felony
شنبه 21 آذر 1388, 20:58 عصر
در مورد ذخیره عکس روش بهتری سرغ ندارید؟
منظورتون از روش بهتر چی هست ؟ مگه الان درست کار نمیکنه ؟
hadisalahi2
شنبه 21 آذر 1388, 22:40 عصر
مشکل توی اینه که روی این پنل که موضوعات در اون قرار میگیرند یک tabPage قرارداره که دکمه های اصلی روی اون قرار داره . حالا هنگام ذخیره تصویر باید Page باز بشه و مقداری روی Panel قرار میگیره.
به همین علت هنگام ذخیره کنترلها در فایل عکس ، تصویر اون قسمتی رو که Page روی پنل قرار میگیره سفید میشه و تصویر کامل ذخیره نمیشه.
مثل شکل زیر
نحوه ذخیر شدن عکس رو نمایش میده
Felony
شنبه 21 آذر 1388, 23:11 عصر
عکس دومی که گزاشتید و عکس ناقص ذخیره شده هست ، اون قسمت پنلتون هست ؟یعنی اون اشیاء روی پنل هستند ؟ چه طور اونها رو رسم کردید ؟ ( اونها شئ Image هستن که به صورت Runtime ساخته شدن ) ؟
در کل اگر اینطوره این نوع ذخیره شدن عکس طبیعی هست ، چون اگر کد رو تحلیل کنید ما داریم از DC اون شئ استفاده میکنیم .
یا باید در کل روش کارتون رو عوض کنید ، یا قبل از ذخیره عکس TabPage رو مخفی و بعد عکس رو ذخیره و دوباره TabPage رو نمایش بدید .
موفق باشید .
hadisalahi2
یک شنبه 22 آذر 1388, 08:27 صبح
عکس دومی که گزاشتید و عکس ناقص ذخیره شده هست ، اون قسمت پنلتون هست ?
بله دقیقا همون قسمت سفید مربوط به همون Page ای که گفتاده روی اون و سفید شده. و کامل ذخیره نشده در فایل.
یعنی اون اشیاء روی پنل هستند ؟ چه طور اونها رو رسم کردید ؟ ( اونها شئ Image هستن که به صورت Runtime ساخته شدن ) ؟
بله اون گاوصندوق ها و اون کمده که ناقص نمایش داده شده ، اشیاء روی پنل هستند و اونها رو در حالت Runtime هنگامی که کاربرروی دکمه هر شکل کلیک میکنه ایجاد میکنم.
در کل اگر اینطوره این نوع ذخیره شدن عکس طبیعی هست ، چون اگر کد رو تحلیل کنید ما داریم از DC اون شئ استفاده میکنیم .
منظورتون از DC چیه؟
یا باید در کل روش کارتون رو عوض کنید ، یا قبل از ذخیره عکس TabPage رو مخفی و بعد عکس رو ذخیره و دوباره TabPage رو نمایش بدید .
در مورد تغییر روش کار که چون یاد نداشتم سوال کردم.
همچنین قبل از ذخیره پانل اون قسمتهایی رو که روی پنل قرار میگیره رو مخفی کردم ولی بازهم تغییری حاصل نشد.
در ضمن در مورد اومن چاپ هم هنوز خطا میده ، روش دیگه ای واسه چاپ سراغ ندارید؟
ممنون میشم.
یا علی
Felony
یک شنبه 22 آذر 1388, 08:48 صبح
منظورتون از DC چیه؟
DC مخفف کلمه ی Device Context هست ، برای اطلاعات جزئی به MSDN مراجعه کنید ، در کل تابع GetDC هندل قسمت رسم شده ی یک کنترل رو به ما برمیگردونه که ما در کد ازش برای رسم در Canvas استفاده کردیم .
در مورد تغییر روش کار که چون یاد نداشتم سوال کردم.
میتونید صفحه ی Design رو جدا طراحی کنید ، میتونید اون TabPage رو به صورت Dockable طراحی کنید و بهترین گزینه اینکه قبل از پرینت یا ذخیره در فایل یه پیش نمایش ( PrintPreview ) از صقحه طراحی شده در یک فرم جدا به کاربر بدید و بعد از تائید کاربر اون پیش نمایش رو ذخیره کنید .
در ضمن در مورد اومن چاپ هم هنوز خطا میده ، روش دیگه ای واسه چاپ سراغ ندارید؟
راه همینه ، شما تو یه سیستم دیگه هم چک کن .
دوستان یه نگاهی به کد بندازن شاید مثلا باید چیزی رو در Printer به صورت پیش فرض مقدار دهی کرد یا ... ، ولی تا اونجا که من یادمه و تست کردم این کد درسته .
hadisalahi2
یک شنبه 22 آذر 1388, 09:10 صبح
میتونید صفحه ی Design رو جدا طراحی کنید ، میتونید اون TabPage رو به صورت Dockable طراحی کنید و بهترین گزینه اینکه قبل از پرینت یا ذخیره در فایل یه پیش نمایش ( PrintPreview ) از صقحه طراحی شده در یک فرم جدا به کاربر بدید و بعد از تائید کاربر اون پیش نمایش رو ذخیره کنید .
چطوری میتونم کنترلهای داخل یک پنل رو به داخل یک پنل مجزا انتقال بدم؟
Felony
یک شنبه 22 آذر 1388, 10:11 صبح
برای انتقال کافیه که Parent کنترل های روی پنل جاری رو = پنل مورد نظر قرار بدید :
var
I: Integer;
begin
for I := Panel1.ControlCount-1 downto 0 do
begin
Panel1.Controls[i].Parent := Panel2 ;
end;
end;
hadisalahi2
یک شنبه 22 آذر 1388, 11:06 صبح
روش پیشنهادی روش خوبیه ولی مشکل توی اینه که هر دفعه بعد از انتقال Parent به Panel دوم ، باید مجددا Parent موضوعات به حالت اول برگردانده شود.
در کل ارزشش رو داره .
در مورد روش چاپ مستقیم روش بهتری سراغ ندارید؟
چون همچنان در سیستم دیگه هم همون پیغام رو میده
یا علی
Felony
یک شنبه 22 آذر 1388, 11:27 صبح
من یک بار دیگه کد رو خوندم ، این قسمت رو حواسم نبود و ساخت شئ Printer و Canvas رو داخل بلوک Try انجام دادم ، کد اصلاح شده رو تست بکنید ، شاید مشکل از اون باشه :
procedure SaveControlImageToFile(AControl:TWinControl);
Var
Canvas : TCanvas;
Pri : TPrinter;
Begin
Canvas:=TCanvas.Create;
Pri:=TPrinter.Create;
try
Canvas.Handle := GetDc(AControl.Handle);
Pri.BeginDoc;
Pri.Canvas.CopyRect(Canvas.ClipRect,Canvas,Canvas. ClipRect );
Pri.EndDoc;
finally
ReleaseDC(AControl.Handle,Canvas.Handle);
Pri.Free;
end;
end;
hadisalahi2
یک شنبه 22 آذر 1388, 11:53 صبح
نه عزیز فرقی نکرد بازهم همون پیغام خطا رو میده.
Felony
یک شنبه 22 آذر 1388, 11:58 صبح
نه عزیز فرقی نکرد بازهم همون پیغام خطا رو میده.
یک نمونه برنامه بنویسید با این کد که میگید خطا میده و اینجا قرار بدید .
hadisalahi2
یک شنبه 22 آذر 1388, 12:08 عصر
در ضمن پرینتر من Hp Laserjet 1018 است.
Felony
یک شنبه 22 آذر 1388, 15:31 عصر
احتمالا ویندوزتون مشکل داره ، هر چی هست مشکل از کد نیست ، من تست کردم درست کار کرد ، شاید پرینتر رو به صورت پیش فرض انتخاب نکردید ، تو کد با متد PrinterIndex پرینتر رو قبل از شروع پرینت ( BeginDoc ) انتخاب کن ببین چی میشه .
یه نرم افزار پرینتر مجازی مثل PDF Creator نصب کنید و با اون تست کنید ببینید چی میشه .
در هر صورت در سیستم من که با پرینتر مجازی به راحتی پرینت گرفت .
hadisalahi2
یک شنبه 22 آذر 1388, 17:45 عصر
احتمالا ویندوزتون مشکل داره ، هر چی هست مشکل از کد نیست ، من تست کردم درست کار کرد ، شاید پرینتر رو به صورت پیش فرض انتخاب نکردید ، تو کد با متد PrinterIndex پرینتر رو قبل از شروع پرینت ( BeginDoc ) انتخاب کن ببین چی میشه .
یه نرم افزار پرینتر مجازی مثل PDF Creator نصب کنید و با اون تست کنید ببینید چی میشه .
در هر صورت در سیستم من که با پرینتر مجازی به راحتی پرینت گرفت .
با پرینتر مجازی آفیس هم تست کردم بازهم همین خطا رو میده.
شما با پرینتر واقعی تست کردید یا پرینتر مجازی؟
Felony
یک شنبه 22 آذر 1388, 18:14 عصر
با پرینتر مجازی آفیس هم تست کردم بازهم همین خطا رو میده.
شما با پرینتر واقعی تست کردید یا پرینتر مجازی؟
پرینتر در دسترس نداشتم و با پرینتر مجازی تست کردم ، ولی باز هم میگم کد درسته !
tdkhakpur
یک شنبه 22 آذر 1388, 18:46 عصر
احتمال دارد سرعت free سازی پرینتر خیلی بالا باشد برای این کار شما ایجاد شی پرینتر را در هنگام create فرم و free شدن آنرا موقع Close فرم انجام بدید
var
Pri : TPrinter; // گلوبال
procedure TForm1.FormCreate(Sender: TObject);
begin
Pri:=TPrinter.Create;
end;
procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
begin
Pri.Free;
end;
وتابع چاپ بر روی پرینتر این شکلی بشود.
procedure SaveControlImageToFile(AControl:TWinControl);
Var
Canvas : TCanvas;
Begin
Canvas:=TCanvas.Create;
Canvas.Handle := GetDc(AControl.Handle);
Pri.BeginDoc;
Pri.Canvas.CopyRect(Canvas.ClipRect,Canvas,Canvas. ClipRect );
Pri.EndDoc;
ReleaseDC(AControl.Handle,Canvas.Handle);
end;
hadisalahi2
دوشنبه 23 آذر 1388, 19:28 عصر
احتمال دارد سرعت free سازی پرینتر خیلی بالا باشد برای این کار شما ایجاد شی پرینتر را در هنگام create فرم و free شدن آنرا موقع Close فرم انجام بدید
نه عزیز. کد شما رو هم امتحان کردم فایده ای نداشت.
باز هم خطای AV .
از دوستان خواهش میکنم فایلی رو که آپلود کردم ، دانلود کرده و در سیستم خودشون تست کنند . تامطمئن بشم مشکل از سیستم منه.
البته دوست عزیزSilver Soft تست کردن و میخوام برای اطمینان بیشتر دوستان هم این زحمت رو بکشند.
یا علی
mrahda
دوشنبه 12 بهمن 1388, 09:57 صبح
احتمالا پرينتر روي كامپيوترت نصب نكردي كه نمي تونه BeginDoc كنه.
Mahmood_M
دوشنبه 12 بهمن 1388, 14:31 عصر
من هم تست کردم و مشکلی نداشت ، برنامه رو Trace کنید ، ببینید دقیقا روی کدوم خط خطا می ده ...
...
hadisalahi2
دوشنبه 12 بهمن 1388, 17:05 عصر
دقیقا در خط زیر پیغام خطا میده
Pri.BeginDoc;
دوستان اگه زحمتی نیست یک پروژه در سیستم خودشون با همین کد اجرا کنند و اون رو اگه زحمتی نیست اینجا آپلود کنند تا بفهمم مشکل از کجاست
یا حق
vBulletin® v4.2.5, Copyright ©2000-1404, Jelsoft Enterprises Ltd.