حفظ قائمة الصور في دلفي
الكاتب:Eve Cole
وقت التحديث:2025-02-03 12:00:04
مؤخرًا، أثناء العمل في مشروع، واجهت موقفًا يتمثل في حفظ سلسلة من الصور في قائمة الصور (TIImageList) في ملف محدد أو دفق ثنائي بحيث يمكن استعادتها ديناميكيًا عند الحاجة. لذلك قمت بالبحث عن الخصائص والأساليب المتعلقة بفئة TImageList في تعليمات دلفي، ولسوء الحظ، لم توفر دلفي أساليب SaveToFile وSaveToStream في TImageList، لذلك، نظرًا للقيود الحالية لـ TImageList، يجب اعتماد طرق أخرى لتوسيع نطاق وظائف TImageList لتلبية متطلبات المشروع الفعلية. |
استخدم وظائف API ImageList_Write وImageList_Read. يحتاج كلاهما إلى تحديد معلمة من النوع IStream، وتتمثل وظيفة الأول في حفظ قائمة الصور الخاصة بالمقبض المحدد في دفق ثنائي من النوع IStream؛ والأخير هو قراءة قائمة الصور المحفوظة في الأصل من الدفق الثنائي من النوع IStream . ، ويعيد مؤشرًا إلى قائمة الصور هذه. IStream هو كائن OLE، وإعلانه في دلفي هو TStreamAdapter = class(TInterfacedObject, IStream)، مما يعني أن TStreamAdapter هو كائن موروث من TInterfacedObject الذي يعالج واجهة IStream. من خلال كائن TStreamAdapter، يمكن تحقيق معالجة كائن واجهة ISTream بواسطة كائن TStream الداخلي في دلفي. |
وراثة فئة فرعية TImageListEx من TImageList وتنفيذ أساليب SaveToFileEx وSaveToStreamEx المخصصة. افتراضيًا، تتكون الصور المحفوظة في TImageList من صور عادية وصور القناع الخاصة بها، لذلك يجب استدعاء GetImages(Index: Integer; Image, Mask: المقدمة من الجزء المحمي من فئتها الأساسية TCustomImageList) TBitmap) للحصول على الصورة النقطية برقم الفهرس المحدد في قائمة الصور والصور النقطية للقناع الخاص بها، ثم حفظها في ملف مخصص أو دفق ثنائي على التوالي. بالإضافة إلى ذلك، فإن طريقتي LoadFromFileEx وLoadFromStreamEx مطلوبتان أيضًا للحصول على الصورة النقطية من استعادة الملف المخصص أو الدفق الثنائي. |
يقوم عنصر التحكم TImageListEx المخصص بتغليف الطريقتين المذكورتين أعلاه في الجزء العام. |
الكود المصدري لفئة TImageListEx هو كما يلي: |
يستخدم Windows، SysUtils، Classes، Graphics، Controls، Commctrl، ImgList، Consts؛ |
TImageListEx = فئة (TIImageList) |
الإجراء LoadFromFile(const FileName: string);// تنفيذ طريقة API للحفظ |
الإجراء LoadFromStream(Stream: TStream); |
الإجراء SaveToFile(const FileName: string); |
إجراء SaveToStream(Stream: TStream); |
الإجراء LoadFromFileEx(const FileName: string);// تحقيق طريقة حفظ مخصصة |
الإجراء LoadFromStreamEx(Stream: TStream); |
الإجراء SaveToFileEx(const FileName: string); |
إجراء SaveToStreamEx(Stream: TStream); |
RegisterComponents('ImageListEx', [TIImageListEx]); |
الإجراء TImageListEx.LoadFromFile(const FileName: string); |
الدفق := TFileStream.Create(FileName, fmOpenRead); |
الإجراء TImageListEx.LoadFromFileEx(const FileName: string); |
الدفق := TFileStream.Create(FileName, fmOpenRead); |
LoadFromStreamEx(Stream); |
الإجراء TImageListEx.LoadFromStream(Stream: TStream); |
SA := TStreamAdapter.Create(Stream); |
Handle := ImageList_Read(SA);// قم بتوجيه مقبض قائمة الصور الحالية إلى المقبض الذي تم الحصول عليه من الدفق الثنائي |
رفع EReadError.CreateRes(@SImageReadFail); |
الإجراء TImageListEx.LoadFromStreamEx(Stream: TStream); |
العرض، الارتفاع: عدد صحيح؛ |
الصورة النقطية، القناع: TBitmap؛ |
BinStream: TMemoryStream؛ |
الإجراء LoadImageFromStream(Image: TBitmap); |
Stream.ReadBuffer(Count, SizeOf(Count));// اقرأ أولاً حجم الصورة النقطية |
BinStream.CopyFrom(Stream, Count);// ثم اقرأ الصورة النقطية |
BinStream.Position := 0; // إعادة تعيين مؤشر الدفق |
Image.LoadFromStream(BinStream); |
Stream.ReadBuffer(Height, SizeOf(Height)); |
Stream.ReadBuffer(Width, SizeOf(Width)); |
الارتفاع الذاتي := الارتفاع؛ |
Self.Width := Width;// استعادة الارتفاع والعرض الأصليين لقائمة الصور |
الصورة النقطية := TBitmap.Create; |
القناع := TBitmap.Create; |
BinStream := TMemoryStream.Create; |
بينما Stream.Position <> Stream.Size يفعل ذلك |
LoadImageFromStream(Bitmap);// قراءة الصورة النقطية من الدفق الثنائي |
LoadImageFromStream(Mask);// اقرأ الصورة النقطية للقناع من الدفق الثنائي |
Add(Bitmap, Mask);// أضف الصورة النقطية وصورة القناع النقطية إلى قائمة الصور |
الإجراء TImageListEx.SaveToFile(const FileName: string); |
الدفق := TFileStream.Create(FileName, fmCreate); |
الإجراء TImageListEx.SaveToFileEx(const FileName: string); |
الدفق := TFileStream.Create(FileName, fmCreate); |
الإجراء TImageListEx.SaveToStream(Stream: TStream); |
SA := TStreamAdapter.Create(Stream); |
إذا لم يكن ImageList_Write(Handle, SA) ثم // احفظ قائمة الصور الحالية في الدفق الثنائي |
رفع EWriteError.CreateRes(@SImageWriteFail); |
الإجراء TImageListEx.SaveToStreamEx(Stream: TStream); |
العرض، الارتفاع: عدد صحيح؛ |
الصورة النقطية، القناع: TBitmap؛ |
BinStream: TMemoryStream; |
الإجراء SetImage(Image: TBitmap; IsMask: Boolean); |
Image.Assign(nil);// امسح آخر صورة محفوظة لتجنب تداخل الصورة |
if IsMask ثم MonoChrome := True;// يجب أن تستخدم الصورة النقطية للقناع أحادية اللون |
الإجراء SaveImageToStream(Image: TBitmap); |
Image.SaveToStream(BinStream); |
Stream.WriteBuffer(Count, SizeOf(Count));// احفظ أولاً حجم الصورة النقطية |
Stream.CopyFrom(BinStream, 0);// ثم احفظ الصورة النقطية |
Stream.WriteBuffer(Height, SizeOf(Height));// احفظ ارتفاع قائمة الصور الأصلية |
Stream.WriteBuffer(Width, SizeOf(Width));// احفظ عرض قائمة الصور الأصلية |
الصورة النقطية := TBitmap.Create; |
القناع := TBitmap.Create; |
BinStream := TMemoryStream.Create; |
for I := 0 to Count - 1 do//احفظ الصورة في قائمة الصور |
GetImages(I, Bitmap, Mask);// احصل على الصورة النقطية برقم الفهرس المحدد والصورة النقطية للقناع الخاص بها |
SaveImageToStream(Bitmap);// احفظ الصورة النقطية في الدفق الثنائي |
SaveImageToStream(Mask);// احفظ الصورة النقطية للقناع في الدفق الثنائي |
يوضح ما يلي كيفية استخدامه في دلفي: |
قم أولاً بإنشاء مشروع جديد في دلفي، ثم قم بوضع عنصر تحكم ImageListEx وعنصر تحكم TreeView وأربعة عناصر تحكم Button في Form1. قم بإقران خاصية الصور لعنصر التحكم TreeView مع ImageListEx، وأضف أي عدد من الصور إلى ImageListEx، وأضف عددًا مطابقًا من العناصر إلى TreeView. تتوافق خصائص ImageIndex للعناصر مع أرقام فهرس الصور في ImageListEx. الآن يمكن عرض الرمز المقابل قبل كل عنصر في TreeView. |
وأخيرًا، اكتب في حدث OnClick الخاص بـ Button1: |
ImageListEx1.SaveToFile('C:CJ.dat'); |
ImageListEx1.SaveToFileEx('C:CJEx.dat'); |
في الحدث OnClick Button2 اكتب: ImageListEx1.Clear; |
اكتب في حدث OnClick الخاص بـ Button3: ImageListEx1.LoadFromFile('C:CJ.dat'); |
اكتب في حدث OnClick الخاص بـ Button4: ImageListEx1.LoadFromFileEx('C:CJEx.dat'); |
قم بتشغيل البرنامج، انقر أولاً فوق Button1، ثم انقر فوق Button2، وأخيرًا انقر فوق Button3 أو Button4. يمكنك أن ترى أن البرنامج يمكنه حفظ الصور في قائمة الصور إلى الملف المحدد، ويمكنه استعادتها وعرضها بشكل صحيح من الملف المحدد. . |
تم استخدام المحتوى المقدم في هذه المقالة لحل الموقف الذي واجهته في المشاريع الفعلية، وآمل أيضًا أن يتمكن المبرمجون الذين يواجهون هذه المشكلة أيضًا من العثور على الإجابة منه. لقد اجتاز التعليمة البرمجية أعلاه عملية التصحيح والتشغيل في Delphi5.0 وWindows2000 Server. |