Recent

Author Topic: [SOLVED] Resource files in Lazarus  (Read 10044 times)

PatBayford

  • Full Member
  • ***
  • Posts: 125
[SOLVED] Resource files in Lazarus
« on: May 22, 2018, 12:17:18 am »
How do I extract individual bitmaps from a loaded resource file please? Used to be easy using the Windows API LoadBitmap function, but Lazarus does not support this, presumably as part of the multi-platform drive.
In fact, I would like to get hold of a good reference to Resource file use in Lazarus - anybody come across one?
« Last Edit: May 22, 2018, 02:38:20 am by PatBayford »
Lazarus 1.8.0 FPC 3.0.2 SVN 56594 Windows 10 64bit (i386-win32-win32/win64)

wp

  • Hero Member
  • *****
  • Posts: 11830
Re: Resource files in Lazarus
« Reply #1 on: May 22, 2018, 12:39:14 am »
How do I extract individual bitmaps from a loaded resource file please?
Code: Pascal  [Select][+][-]
  1. procedure TForm1.Button1Click(Sender: TObject);
  2. var
  3.   pic: TPicture;
  4. begin
  5.   pic := TPicture.Create;
  6.   pic.LoadFromResourceName(HINSTANCE, 'BTN_YES');   // <---- read the resource of the program
  7.   Image1.Picture.Assign(pic);
  8.   pic.Free;
  9. end;

PatBayford

  • Full Member
  • ***
  • Posts: 125
Re: Resource files in Lazarus
« Reply #2 on: May 22, 2018, 02:37:57 am »
Thanks wp - came up with that route myself - works fine. Just wanted to make sure there was not some other, more direct route.
Lazarus 1.8.0 FPC 3.0.2 SVN 56594 Windows 10 64bit (i386-win32-win32/win64)

wp

  • Hero Member
  • *****
  • Posts: 11830
Re: Resource files in Lazarus
« Reply #3 on: May 22, 2018, 09:20:40 am »
Thanks wp - came up with that route myself - works fine. Just wanted to make sure there was not some other, more direct route.
More direct than a one-liner?

Thaddy

  • Hero Member
  • *****
  • Posts: 14159
  • Probably until I exterminate Putin.
Re: [SOLVED] Resource files in Lazarus
« Reply #4 on: May 22, 2018, 10:00:20 am »
 8) And it deserves a link to https://www.youtube.com/watch?v=b19PcuJsQbA
Specialize a type, not a var.

ccrause

  • Hero Member
  • *****
  • Posts: 843
Re: Resource files in Lazarus
« Reply #5 on: May 22, 2018, 11:30:04 am »
Just wanted to make sure there was not some other, more direct route.

An alternative route to working with resources:
Code: Pascal  [Select][+][-]
  1. var
  2.   Resource: TResourceStream;
  3. begin
  4.   Resource := TResourceStream.CreateFromID(HInstance, ResID, PChar(ResourceName));
  5.   // the resource is now in a stream, so one can assign, save, read etc.
  6.   Resource.SaveToFile('ImportantData.bin');
  7. ...
This gives you direct access (AFAIK, there may be exceptions) to all resources compiled into the application.

Thaddy

  • Hero Member
  • *****
  • Posts: 14159
  • Probably until I exterminate Putin.
Re: [SOLVED] Resource files in Lazarus
« Reply #6 on: May 22, 2018, 12:26:55 pm »
There used to be exceptions(like Windows only...) , but there aren't any anymore (afaik). Resources are even handled correctly cross-platform.(afaik)
Specialize a type, not a var.

torbente

  • Sr. Member
  • ****
  • Posts: 325
    • Noso Main Page
Re: [SOLVED] Resource files in Lazarus
« Reply #7 on: December 02, 2021, 11:47:58 pm »
Sorry for push this old topic, but i search and was unable to find nothing:
I developed a custom procedure to get resources and save it to a file:
(the file included in the resources were added via Project->Options->Resources->Add

Code: Pascal  [Select][+][-]
  1. Procedure CreateFileFromResource(resourcename,filename:string);
  2. var
  3.   Resource: TResourceStream;
  4. begin
  5. try
  6.  
  7.   Resource := TResourceStream.Create(HInstance, resourcename, RT_RCDATA);
  8.   Resource.Position := 0;
  9.   Resource.SaveToFile(filename);
  10. finally
  11.   Resource.Free;
  12. end;
  13.  
  14. End;
  15.  

This only works if i include the unit windows in the Uses section. If not, i get the error:

Code: Pascal  [Select][+][-]
  1. nggmainform.pas(45,63) Error: Identifier not found "RT_RCDATA"

Any fix that could work cross-platform?

Thanks a lot
Noso Cryptocurrency Main Developer
https://github.com/DevTeamNoso/NosoWallet

Gustavo 'Gus' Carreno

  • Hero Member
  • *****
  • Posts: 1088
  • Professional amateur ;-P
Re: [SOLVED] Resource files in Lazarus
« Reply #8 on: December 03, 2021, 12:04:17 am »
Hey Torbente,

Any fix that could work cross-platform?

After following the white rabbit through the hole that is the fpcsrc I found out that:
Code: Pascal  [Select][+][-]
  1. const
  2.   RT_RCDATA = MAKEINTRESOURCE(10);

So obviously, I then tried to find where MAKEINTRESOURCE was and found out that it just a new type:
Code: Pascal  [Select][+][-]
  1. type
  2.   MAKEINTRESOURCE = pchar;

So you can now remove the dependency from the Windows unit and change your code to:
Code: Pascal  [Select][+][-]
  1. Procedure CreateFileFromResource(resourcename,filename:string);
  2. const
  3.   RT_RCDATA = PChar(10);
  4. var
  5.   Resource: TResourceStream;
  6. begin
  7. try
  8.  
  9.   Resource := TResourceStream.Create(HInstance, resourcename, RT_RCDATA);
  10.   Resource.Position := 0;
  11.   Resource.SaveToFile(filename);
  12. finally
  13.   Resource.Free;
  14. end;

After that, it will work cross-platform.

Cheers,
Gus
Lazarus 3.99(main) FPC 3.3.1(main) Ubuntu 23.10 64b Dark Theme
Lazarus 3.0.0(stable) FPC 3.2.2(stable) Ubuntu 23.10 64b Dark Theme
http://github.com/gcarreno

Sieben

  • Sr. Member
  • ****
  • Posts: 310
Re: [SOLVED] Resource files in Lazarus
« Reply #9 on: December 03, 2021, 12:20:37 am »
RT_RCDATA is also defined in LCLType:

Code: Pascal  [Select][+][-]
  1. {$ifdef windows}
  2.   RT_CURSOR = Windows.RT_CURSOR;
  3.   RT_BITMAP = Windows.RT_BITMAP;
  4.   //...
  5.   RT_RCDATA = Windows.RT_RCDATA;
  6.   //...
  7. {$else}
  8.   RT_CURSOR = TResourceType(1);
  9.   RT_BITMAP = TResourceType(2);
  10.   //...
  11.   RT_RCDATA = TResourceType(10);
  12.   //...
Lazarus 2.2.0, FPC 3.2.2, .deb install on Ubuntu Xenial 32 / Gtk2 / Unity7

circular

  • Hero Member
  • *****
  • Posts: 4181
    • Personal webpage
Re: [SOLVED] Resource files in Lazarus
« Reply #10 on: December 03, 2021, 08:14:38 am »
As a side note, BGRABitmap makes it easy to access resources, wether they are imported from LRS or RES files. The unit BGRABitmapTypes exposes BGRAResource instance that can return a resource by its filename:
Code: Pascal  [Select][+][-]
  1. type
  2.   { TBGRAResourceManager }
  3.  
  4.   TBGRAResourceManager = class
  5.   protected
  6.     function GetWinResourceType(AExtension: string): pchar;
  7.   public
  8.     function GetResourceStream(AFilename: string): TStream; virtual;
  9.     function IsWinResource(AFilename: string): boolean; virtual;
  10.   end;
  11.  
  12. var
  13.   BGRAResource : TBGRAResourceManager;

You can use it as:
Code: Pascal  [Select][+][-]
  1. implementation
  2.  
  3. {$R *.lfm}
  4.  
  5. uses BGRABitmap, BGRABitmapTypes, LResources;
  6.  
  7. { TForm1 }
  8.  
  9. procedure TForm1.FormPaint(Sender: TObject);
  10. var bmp: TBGRABitmap;
  11. begin
  12.   bmp := TBGRABitmap.Create;
  13.   bmp.LoadFromResource('shape.png');
  14.   bmp.Draw(Canvas, 0,0, False);
  15.   bmp.Free;
  16. end;
  17.  
  18. initialization
  19.  
  20. {$I myresource.lrs} // contains "shape.png"
  21.  
  22. end.

When using RES resources, the extension is generally ignored because it is not stored as such in the RES file, but I find it still useful to indicate what kind of data it contains.

LazPaint can save images directly into LRS or RES files (they are treated as folders).
« Last Edit: February 21, 2024, 07:54:51 am by circular »
Conscience is the debugger of the mind

Gustavo 'Gus' Carreno

  • Hero Member
  • *****
  • Posts: 1088
  • Professional amateur ;-P
Re: [SOLVED] Resource files in Lazarus
« Reply #11 on: December 03, 2021, 02:38:50 pm »
Hey Sieben,

RT_RCDATA is also defined in LCLType:

That's awesome to know. I think I may update the wiki's Lazarus Resources page to make that clear.
I think a lot of the confusion comes from that example not mentioning that LCLTypes is better than including Windows.

I thank you OH SO very much for a better rabbit hole diving experience than mine :)

Cheers,
Gus
Lazarus 3.99(main) FPC 3.3.1(main) Ubuntu 23.10 64b Dark Theme
Lazarus 3.0.0(stable) FPC 3.2.2(stable) Ubuntu 23.10 64b Dark Theme
http://github.com/gcarreno

Gustavo 'Gus' Carreno

  • Hero Member
  • *****
  • Posts: 1088
  • Professional amateur ;-P
Re: [SOLVED] Resource files in Lazarus
« Reply #12 on: December 03, 2021, 07:30:28 pm »
Hey Y'all,

I've edited the example on Lazarus Resources, paragraph "Using resources in your program".

I've replaced the Windows unit by the LCLType one on the example and removed now obsolete comments.

Hopefully, this will make the example fully cross-platform.

Cheers,
Gus
Lazarus 3.99(main) FPC 3.3.1(main) Ubuntu 23.10 64b Dark Theme
Lazarus 3.0.0(stable) FPC 3.2.2(stable) Ubuntu 23.10 64b Dark Theme
http://github.com/gcarreno

 

TinyPortal © 2005-2018