Martin
Martin

Reputation: 1085

Add resource file by code with Delphi

I have a custom res file "myres.res". In this moment I use it on my application, I have add {$R myres.res} under {$R *.res} line inside my DPR project file and it work very well.

Now I'd like creare a VCL component with a boolean property "UseCustomRes". If I set UseCustomRes=True I'd like add the res file when I compile my project but if I set UseCustomRes=False I don't want use res file when I compile my project.

Is this possible? I don't know if it possible and how it is possible.

Upvotes: 1

Views: 2734

Answers (2)

David Heffernan
David Heffernan

Reputation: 613562

Resources are included by the linker based on the existence of special $RESOURCE directives. These directives cannot be switched based on the value of an object instance's property.

So, with the built in tooling there is now way to achieve what you desire. What you will need to do is to add a post-build step that modifies the output file by adding the resource if needed. A good example of a tool which does exactly this is madExcept.

Upvotes: 3

Johan
Johan

Reputation: 76753

Picking a resource at runtime
If you want to use a resource (or not) based on a runtime variable you'll have to compile it in always, otherwise you'll lose the option of using it at runtime.

Whilst running you can access a resource using TResourceStream.

Here's an example:

procedure ExtractResource;
var
  rs: TResourceStream;
begin
  rs:= TResourceStream.Create(HInstance, 'NameOfResource', RT_RCDATA);
  try
    rs.Position:= 0;
    rs.DoSomethingWithTheResource...
  finally
    rs.Free;
  end;
end;

Here's the online help: http://docwiki.embarcadero.com/Libraries/XE2/en/System.Classes.TResourceStream
Note that the help entry for TResourceStream is a bit broken; it does not show all methods.
The missing methods are here: http://docwiki.embarcadero.com/Libraries/XE2/en/System.Classes.TStream_Methods

Picking a resource at compile time
Note that the {$R *.res} line includes any .res file in the current directory.
If you want to select a specific .res file, you'll have to exclude this line.
Conditional compilation is done using defines, like so:

 implementation
   {.R *.res}  //disable the *.res inclusion.
   {$IFDEF GetMyResource}
     {$R MyResource.res}   //will only be compiled if `GetMyResource` is defined
   {$ENDIF}
   {$R AlwaysIncludeThisResource.res} //will always be included.

You then define the symbol GetMyResource in the Conditional defines under project options, see here: https://stackoverflow.com/a/4530320/650492

Upvotes: 4

Related Questions