pas2jsresources.pp 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. {$IFNDEF FPC_DOTTEDUNITS}
  2. unit pas2jsresources;
  3. {$ENDIF FPC_DOTTEDUNITS}
  4. {$mode objfpc}{$H+}
  5. interface
  6. {$IFDEF FPC_DOTTEDUNITS}
  7. uses
  8. System.Classes, System.SysUtils,
  9. {$IFDEF pas2js}
  10. web,
  11. {$ELSE}
  12. System.Hash.Base64,
  13. {$ENDIF}
  14. Pas2Js.Files.Fs, Js.Tree;
  15. {$ELSE FPC_DOTTEDUNITS}
  16. uses
  17. Classes, SysUtils,
  18. {$IFDEF pas2js}
  19. web,
  20. {$ELSE}
  21. base64,
  22. {$ENDIF}
  23. pas2jsfs, jsTree;
  24. {$ENDIF FPC_DOTTEDUNITS}
  25. Type
  26. TResourceScopeMode = (rmProgram,rmUnit);
  27. { TPas2jsResourceHandler }
  28. TResourceOutputMode = (romNone,romJS,romFile,romExtraJS);
  29. TPas2jsResourceHandler = class(TObject)
  30. private
  31. FCurrentUnitName: String;
  32. FFS: TPas2JSFS;
  33. Protected
  34. // Must be overridden
  35. function GetResourceCount: Integer; virtual; abstract;
  36. // Content of file, if file based.
  37. function GetAsString: String; virtual; abstract;
  38. // Detect some common formats
  39. Function GetFormat(const aFileName : string; aOptions : TStrings) : string; virtual;
  40. Public
  41. Constructor Create(aFS : TPas2JSFS); virtual;
  42. // Called for every found resource
  43. Procedure HandleResource (aFileName : string; Options : TStrings); virtual; abstract;
  44. // Extension of output file, if file based
  45. Class Function OutputFileExtension : String; virtual;
  46. // True if output is file based (i.e. written to separate file)
  47. Class Function OutputMode : TResourceOutputMode; virtual; abstract;
  48. // Load resource file. Can be used in descendents
  49. Function LoadFile(aFileName : string) : TPas2jsFile;
  50. // Load resource file and encode as base64 string. Can be used in descendents
  51. Function GetFileAsBase64(aFileName : string) : string;
  52. // This is called for every unit.
  53. Procedure StartUnit(Const aUnitName : String); virtual;
  54. // This is called at the start of every unit if OutputIsUnitBased is true.
  55. Procedure ClearUnit; virtual;
  56. // This is called at the end of every unit if OutputIsUnitBased is true. Only once if not.
  57. Procedure DoneUnit(isMainFile : Boolean); virtual;
  58. // This is called when Javascript is written for a unit
  59. Function WriteJS(const aUnitName : String; aModule : TJSElement) : TJSElement; virtual;
  60. // Current unit.
  61. Property CurrentUnitName : String Read FCurrentUnitName;
  62. // Passed at create
  63. property FS : TPas2JSFS Read FFS;
  64. // Return file content for writing to file if IsFileBased
  65. Property AsString : String Read GetAsString;
  66. // Number of resources
  67. Property ResourceCount : Integer Read GetResourceCount;
  68. end;
  69. { TNoResources }
  70. TNoResources = Class(TPas2jsResourceHandler)
  71. Public
  72. Procedure HandleResource (aFileName : string; Options : TStrings); override;
  73. Class Function OutputMode : TResourceOutputMode; override;
  74. function GetResourceCount: Integer; override;
  75. function GetAsString: String; override;
  76. end;
  77. implementation
  78. { TNoResources }
  79. procedure TNoResources.HandleResource(aFileName: string; Options: TStrings);
  80. begin
  81. // Do nothing
  82. if aFileName='' then ;
  83. if Options=nil then ;
  84. end;
  85. class function TNoResources.OutputMode: TResourceOutputMode;
  86. begin
  87. result:=romNone;
  88. end;
  89. function TNoResources.GetResourceCount: Integer;
  90. begin
  91. Result:=0;
  92. end;
  93. function TNoResources.GetAsString: String;
  94. begin
  95. Result:='';
  96. end;
  97. { TPas2jsResourceHandler }
  98. function TPas2jsResourceHandler.GetFormat(const aFileName: string; aOptions: TStrings): string;
  99. Var
  100. E : String;
  101. begin
  102. Result:=aOptions.Values['format'];
  103. if Result='' then
  104. begin
  105. E:=ExtractFileExt(aFileName);
  106. if (E<>'') and (E[1]='.') then
  107. E:=Copy(E,2,Length(E)-1);
  108. if Pos(LowerCase(E),';png;jpg;jpeg;bmp;ico;')>0 then
  109. Result:='image/'+E
  110. else if Pos(LowerCase(E),';htm;html;')>0 then
  111. Result:='text/html'
  112. else if Pos(LowerCase(E),';txt;lpr;pas;pp;')>0 then
  113. Result:='text/text'
  114. else if Pos(LowerCase(E),';js;')>0 then
  115. Result:='application/javascript'
  116. else if Pos(LowerCase(E),';json;')>0 then
  117. Result:='application/javascript'
  118. else
  119. Result:='application/octet-stream';
  120. end;
  121. end;
  122. constructor TPas2jsResourceHandler.Create(aFS: TPas2JSFS);
  123. begin
  124. FFS:=aFS;
  125. end;
  126. class function TPas2jsResourceHandler.OutputFileExtension: String;
  127. begin
  128. Result:='';
  129. end;
  130. function TPas2jsResourceHandler.LoadFile(aFileName: string): TPas2jsFile;
  131. begin
  132. Result:=FS.LoadFile(aFileName,True);
  133. end;
  134. function TPas2jsResourceHandler.GetFileAsBase64(aFileName: string): string;
  135. Var
  136. F : TPas2JSFile;
  137. begin
  138. F:=LoadFile(aFileName);
  139. {$IFDEF pas2js}
  140. Result:=window.atob(F.Source);
  141. {$ELSE}
  142. Result:=EncodeStringBase64(F.Source);
  143. {$ENDIF}
  144. // Do not release, FS will release all files
  145. end;
  146. procedure TPas2jsResourceHandler.ClearUnit;
  147. begin
  148. FCurrentUnitName:='';
  149. end;
  150. procedure TPas2jsResourceHandler.StartUnit(const aUnitName: String);
  151. begin
  152. FCurrentUnitName:=aUnitName;
  153. end;
  154. procedure TPas2jsResourceHandler.DoneUnit(isMainFile: Boolean);
  155. begin
  156. if not isMainFile then
  157. ClearUnit;
  158. end;
  159. function TPas2jsResourceHandler.WriteJS(const aUnitName: String; aModule: TJSElement): TJSElement;
  160. begin
  161. Result:=aModule;
  162. if aUnitName='' then ;
  163. end;
  164. end.