pas2js resources

From Free Pascal wiki

Pas2js - Resources

Compiler

The compiler supports the {$R somefile} directive.

This means that directives like

{$R *.html}

or

{$R left.png}

{$R right.png}

{$R up.png}

{$R down.png}

will attempt to include the specified files.

This mechanism is pluggable, and the compiler currently supports 2 mechanisms:

  • The resources are added to a javascript structure in the generated javascript.
  • The resources are emitted to a file with html snippet. this will look like this:

For a node.js program only the Javascript mechanism can be chosen.

     <link rel="preload" id="resource-testres" data-unit="consoledemo"
href="data:text/html;base64,PGgzPlRlc3QgcmVzb3VyY2UgaW4gSFRNTDwvaDM+ClRoaXMgaXMgYSBtYWluIHByb2dyYW0gZmlsZSByZXNvdXJjZSBpbiBIVE1MLgo=" />
     <link rel="preload" id="resource-testb" data-unit="unitb"
href="data:text/html;base64,PGgzPkhlbGxvIFJlc291cmNlIFdvcmxkIFBhcnQgQjwvaDM+CjxwPgpUaGlzIG1lc3NhZ2UgaXMgc2F2ZWQgaW4gYSByZXNvdXJjZSBmaWxlIChQYXJ0IEIpLgo8L3A+Cgo=" />
     <link rel="preload" id="resource-testa" data-unit="unita"
href="data:text/html;base64,PGgzPkhlbGxvIFJlc291cmNlIFdvcmxkIFBhcnQgQTwvaDM+CjxwPgpUaGlzIG1lc3NhZ2UgaXMgc2F2ZWQgaW4gYSByZXNvdXJjZSBmaWxlIChQYXJ0IEEpLgo8L3A+Cgo=" />

This html can be pasted into the HTML file of your project. Or the HTML snippet can be loaded dynamically. In both cases, the resource is base64-encoded before including it.

Command-line options

You can select the resource mechanism to use using the -JR mechanism:

 -Jr<x> Control writing of linked resources

There are 3 options for the x value:

  • none: Do not write resources
  • js: Write resources in Javascript structure
  • html=filename : Write resources as preload links in the specified HTML file.
The HTML filename can be omitted, by default projectfile-res.html is used.

API

The p2jsres unit contains the API to access the resources that were linked in at compile time.

Function SetResourceSource(aSource : TResourceSource) : TResourceSource;

Function GetResourceNames : TStringDynArray;
Function GetResourceNames(aSource : TResourceSource) : TStringDynArray;

Function EnumResources(aCallback : TResourceEnumCallBack) : Integer;
Function EnumResources(aSource : TResourceSource; aCallback : TResourceEnumCallBack) : Integer;

Function GetResourceInfo(Const aName : String; var aInfo : TResourceInfo) : Boolean;
Function GetResourceInfo(aSource : TResourceSource; Const aName : String; var aInfo : TResourceInfo) : Boolean;

Procedure LoadHTMLLinkResources(const aURL : String; OnLoad : TResourcesLoadedEnumCallBack = Nil; OnError : TResourcesLoadErrorCallBack = Nil);

These calls have the following purposes:

  • SetResourceSource can be used to set the mechanism by which the resource values must be accessed. It currently has the following values
* rsJS the resources are embedded in the Javascript.
* rsHTML the resources are embedded in the HTML.
This value is used whenever a call is made that does not specify the resource access mechanism.
  • GetResourceNames can be used to get a list of the available resource names. If aSource is omitted, the source set with SetResourceSource is used.
  • EnumResources calls the callback aCallBack for every resource found. If aSource is omitted, the source set with SetResourceSource is used.
  • GetResourceInfo* returns resource info for resource aName in the structure aInfo. If aSource is omitted, the source set with SetResourceSource is used.
  • LoadHTMLLinkResources will load HTML resources from URL aURL, and will call OnLoad if the resources were successfully loaded, or OnError when the loading failed.

The API is the same for both kind of resources, this is transparant, but you must decide what kind of resources you want to use. You can mix the 2 kinds of resources, although this is not recommended.


Examples

There are 3 example programs in the demo directories which demonstrate the API. They can be viewed on-line

Using javascript-embedded resources

Using HTML <link> resources

Using dynamically loaded HTML <link> resources

There is also a nodejs demo, but this one needs to be compiled from source and run on your local machine.

Extending the compiler

The compiler handles the resource linking by invoking a callback for the $R linking directive. Currently, only 2 kinds of resources are supported, but it is possible to extend this by creating additional callbacks for the compiler.

The following extensions are planned:

  • Support {$R *.res}
This will need to extract the actual resources from the *.res file and add them separately to the JS/HTML.
  • Add support in the Lazarus IDE to specify what resources you want to use,
and automatically include the generated HTML snippet into the project HTML.

Navigation