GLS.ShaderCustom.pas 25 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754
  1. //
  2. // This unit is part of the GLScene Engine, http://glscene.org
  3. //
  4. unit GLS.ShaderCustom;
  5. (*
  6. A collection of pure abstract classes - descendants of TGLShader, which are
  7. used for purpose of not having to write the same stuff all over and over
  8. again in your own shader classes.
  9. It also contains a procedures and function that can be used in all shaders.
  10. The whole history is logged in a former GLS version of the unit.
  11. *)
  12. interface
  13. {$I GLScene.inc}
  14. uses
  15. Winapi.OpenGL,
  16. Winapi.OpenGLext,
  17. System.Classes,
  18. System.SysUtils,
  19. GLVectorGeometry,
  20. GLVectorTypes,
  21. GLTexture,
  22. GLCadencer,
  23. OpenGLTokens,
  24. GLScene,
  25. GLS.Strings,
  26. GLContext,
  27. GLRenderContextInfo,
  28. GLMaterial,
  29. GLVectorLists,
  30. GLTextureFormat,
  31. GLSL.ShaderParameter;
  32. const
  33. glsShaderMaxLightSources = 8;
  34. type
  35. TGLShaderFogSupport = (sfsEnabled, sfsDisabled, sfsAuto);
  36. TGLTransformFeedBackMode = (tfbmInterleaved, tfbmSeparate);
  37. EGLCustomShaderException = class(EGLShaderException);
  38. TGLCustomShader = class;
  39. TGLVertexProgram = class;
  40. TGLFragmentProgram = class;
  41. TGLGeometryProgram = class;
  42. TGLShaderEvent = procedure(Shader: TGLCustomShader) of object;
  43. TGLShaderUnAplyEvent = procedure(Shader: TGLCustomShader; var ThereAreMorePasses: Boolean) of object;
  44. TGLLightSourceEnum = 1..glsShaderMaxLightSources;
  45. TGLLightSourceSet = set of TGLLightSourceEnum;
  46. (* This interface describes user shaders, in order to be able to access them
  47. via a unified interface. If user shader does not support some option, don't
  48. raise an axception, just ignore it. *)
  49. IGLShaderDescription = interface
  50. ['{04089C64-60C2-43F5-AC9C-38ED46264812}']
  51. procedure SetShaderTextures(const Textures: array of TGLTexture);
  52. procedure GetShaderTextures(var Textures: array of TGLTexture);
  53. procedure SetShaderColorParams(const AAmbientColor, ADiffuseColor, ASpecularcolor: TVector4f);
  54. procedure GetShaderColorParams(var AAmbientColor, ADiffuseColor, ASpecularcolor: TVector4f);
  55. procedure SetShaderMiscParameters(const ACadencer: TGLCadencer; const AMatLib: TGLMaterialLibrary; const ALightSources: TGLLightSourceSet);
  56. procedure GetShaderMiscParameters(var ACadencer: TGLCadencer; var AMatLib: TGLMaterialLibrary; var ALightSources: TGLLightSourceSet);
  57. function GetShaderAlpha: Single;
  58. procedure SetShaderAlpha(const Value: Single);
  59. function GetShaderDescription: string;
  60. end;
  61. // Used in the TGLPostShaderHolder component.
  62. IGLPostShader = interface
  63. ['{68A62362-AF0A-4CE8-A9E1-714FE02AFA4A}']
  64. // Called on every pass.
  65. procedure DoUseTempTexture(const TempTexture: TGLTextureHandle;
  66. TextureTarget: TGLTextureTarget);
  67. // Called to determine if it is compatible.
  68. function GetTextureTarget: TGLTextureTarget;
  69. end;
  70. // A pure abstract class, must be overriden.
  71. TGLCustomShader = class(TGLShader)
  72. private
  73. FFragmentProgram: TGLFragmentProgram;
  74. FVertexProgram: TGLVertexProgram;
  75. FGeometryProgram: TGLGeometryProgram;
  76. FTagObject: TObject;
  77. procedure SetFragmentProgram(const Value: TGLFragmentProgram);
  78. procedure SetGeometryProgram(const Value: TGLGeometryProgram);
  79. procedure SetVertexProgram(const Value: TGLVertexProgram);
  80. function StoreFragmentProgram: Boolean;
  81. function StoreGeometryProgram: Boolean;
  82. function StoreVertexProgram: Boolean;
  83. protected
  84. FDebugMode: Boolean;
  85. procedure SetDebugMode(const Value: Boolean); virtual;
  86. property FragmentProgram: TGLFragmentProgram read FFragmentProgram write SetFragmentProgram stored StoreFragmentProgram;
  87. property VertexProgram: TGLVertexProgram read FVertexProgram write SetVertexProgram stored StoreVertexProgram;
  88. property GeometryProgram: TGLGeometryProgram read FGeometryProgram write SetGeometryProgram stored StoreGeometryProgram;
  89. (* Treats warnings as errors and displays this error,
  90. instead of a general shader-not-supported message. *)
  91. property DebugMode: Boolean read FDebugMode write SetDebugMode default False;
  92. property TagObject: TObject read FTagObject write FTagObject default nil;
  93. public
  94. constructor Create(AOwner: TComponent); override;
  95. destructor Destroy; override;
  96. procedure Assign(Source: TPersistent); override;
  97. procedure LoadShaderPrograms(const VPFilename, FPFilename: string; const GPFilename: string = '');
  98. end;
  99. // A custom shader program.
  100. TGLShaderProgram = class(TPersistent)
  101. private
  102. FParent: TGLCustomShader;
  103. FEnabled: Boolean;
  104. FCode: TStrings;
  105. procedure SetCode(const Value: TStrings);
  106. procedure SetEnabled(const Value: Boolean);
  107. procedure OnChangeCode(Sender: TObject);
  108. protected
  109. function GetOwner: TPersistent; override;
  110. public
  111. procedure LoadFromFile(const AFileName: string);
  112. procedure Apply; virtual;
  113. constructor Create(const AParent: TGLCustomShader); virtual;
  114. destructor Destroy; override;
  115. procedure Assign(Source: TPersistent); override;
  116. published
  117. property Code: TStrings read FCode write SetCode;
  118. property Enabled: Boolean read FEnabled write SetEnabled default False;
  119. end;
  120. TGLVertexProgram = class(TGLShaderProgram)
  121. published
  122. property Code;
  123. property Enabled;
  124. end;
  125. TGLFragmentProgram = class(TGLShaderProgram)
  126. published
  127. property Code;
  128. property Enabled;
  129. end;
  130. TGLGeometryProgram = class(TGLShaderProgram)
  131. private
  132. FInputPrimitiveType: TGLgsInTypes;
  133. FOutputPrimitiveType: TGLgsOutTypes;
  134. FVerticesOut: TGLint;
  135. procedure SetInputPrimitiveType(const Value: TGLgsInTypes);
  136. procedure SetOutputPrimitiveType(const Value: TGLgsOutTypes);
  137. procedure SetVerticesOut(const Value: TGLint);
  138. public
  139. constructor Create(const AParent: TGLCustomShader); override;
  140. published
  141. property Code;
  142. property Enabled;
  143. property InputPrimitiveType: TGLgsInTypes read FInputPrimitiveType write SetInputPrimitiveType default gsInPoints;
  144. property OutputPrimitiveType: TGLgsOutTypes read FOutputPrimitiveType write SetOutputPrimitiveType default gsOutPoints;
  145. property VerticesOut: TGLint read FVerticesOut write SetVerticesOut default 0;
  146. end;
  147. // Wrapper around a parameter of the main program.
  148. TGLCustomShaderParameter = class(TObject)
  149. private
  150. protected
  151. function GetAsVector1f: Single; virtual; abstract;
  152. function GetAsVector2f: TVector2f; virtual; abstract;
  153. function GetAsVector3f: TVector3f; virtual; abstract;
  154. function GetAsVector4f: TVector; virtual; abstract;
  155. function GetAsVector1i: Integer; virtual; abstract;
  156. function GetAsVector2i: TVector2i; virtual; abstract;
  157. function GetAsVector3i: TVector3i; virtual; abstract;
  158. function GetAsVector4i: TVector4i; virtual; abstract;
  159. function GetAsVector1ui: Cardinal; virtual; abstract;
  160. function GetAsVector2ui: TVector2ui; virtual; abstract;
  161. function GetAsVector3ui: TVector3ui; virtual; abstract;
  162. function GetAsVector4ui: TVector4ui; virtual; abstract;
  163. procedure SetAsVector1f(const Value: Single); virtual; abstract;
  164. procedure SetAsVector2f(const Value: TVector2f); virtual; abstract;
  165. procedure SetAsVector3f(const Value: TVector3f); virtual; abstract;
  166. procedure SetAsVector4f(const Value: TVector4f); virtual; abstract;
  167. procedure SetAsVector1i(const Value: Integer); virtual; abstract;
  168. procedure SetAsVector2i(const Value: TVector2i); virtual; abstract;
  169. procedure SetAsVector3i(const Value: TVector3i); virtual; abstract;
  170. procedure SetAsVector4i(const Value: TVector4i); virtual; abstract;
  171. procedure SetAsVector1ui(const Value: Cardinal); virtual; abstract;
  172. procedure SetAsVector2ui(const Value: TVector2ui); virtual; abstract;
  173. procedure SetAsVector3ui(const Value: TVector3ui); virtual; abstract;
  174. procedure SetAsVector4ui(const Value: TVector4ui); virtual; abstract;
  175. function GetAsMatrix2f: TMatrix2f; virtual; abstract;
  176. function GetAsMatrix3f: TMatrix3f; virtual; abstract;
  177. function GetAsMatrix4f: TMatrix4f; virtual; abstract;
  178. procedure SetAsMatrix2f(const Value: TMatrix2f); virtual; abstract;
  179. procedure SetAsMatrix3f(const Value: TMatrix3f); virtual; abstract;
  180. procedure SetAsMatrix4f(const Value: TMatrix4f); virtual; abstract;
  181. procedure SetAsTexture(const TextureIndex: Integer;
  182. const Value: TGLTexture);
  183. procedure SetAsTexture1D(const TextureIndex: Integer;
  184. const Value: TGLTexture);
  185. procedure SetAsTexture2D(const TextureIndex: Integer;
  186. const Value: TGLTexture);
  187. procedure SetAsTexture3D(const TextureIndex: Integer;
  188. const Value: TGLTexture);
  189. procedure SetAsTextureCube(const TextureIndex: Integer;
  190. const Value: TGLTexture);
  191. procedure SetAsTextureRect(const TextureIndex: Integer;
  192. const Value: TGLTexture);
  193. function GetAsCustomTexture(const TextureIndex: Integer;
  194. TextureTarget: TGLTextureTarget): Cardinal; virtual; abstract;
  195. procedure SetAsCustomTexture(const TextureIndex: Integer;
  196. TextureTarget: TGLTextureTarget; const Value: Cardinal); virtual; abstract;
  197. function GetAsUniformBuffer: Cardinal; virtual; abstract;
  198. procedure SetAsUniformBuffer(UBO: Cardinal); virtual; abstract;
  199. public
  200. (* This overloaded SetAsVector accepts open array as input. e.g.
  201. SetAsVectorF([0.1, 0.2]). Array length must between 1-4. *)
  202. procedure SetAsVectorF(const Values: array of Single); overload;
  203. procedure SetAsVectorI(const Values: array of Integer); overload;
  204. // SetToTextureOf determines texture type on-the-fly.
  205. procedure SetToTextureOf(const LibMaterial: TGLLibMaterial; const TextureIndex: Integer); overload;
  206. procedure SetToTextureOf(const Texture: TGLTexture; const TextureIndex: Integer); overload;
  207. // GLScene-friendly properties.
  208. property AsVector: TVector read GetAsVector4f write SetAsVector4f;
  209. property AsAffineVector: TAffineVector read GetAsVector3f write SetAsVector3f;
  210. // Standard types.
  211. property AsFloat: Single read GetAsVector1f write SetAsVector1f;
  212. property AsInteger: Integer read GetAsVector1i write SetAsVector1i;
  213. // Float vector types.
  214. property AsVector1f: Single read GetAsVector1f write SetAsVector1f;
  215. property AsVector2f: TVector2f read GetAsVector2f write SetAsVector2f;
  216. property AsVector3f: TVector3f read GetAsVector3f write SetAsVector3f;
  217. property AsVector4f: TVector4f read GetAsVector4f write SetAsVector4f;
  218. // Integer vector types.
  219. property AsVector1i: Integer read GetAsVector1i write SetAsVector1i;
  220. property AsVector2i: TVector2i read GetAsVector2i write SetAsVector2i;
  221. property AsVector3i: TVector3i read GetAsVector3i write SetAsVector3i;
  222. property AsVector4i: TVector4i read GetAsVector4i write SetAsVector4i;
  223. // Unsigned integer vector types.
  224. property AsVector1ui: Cardinal read GetAsVector1ui write SetAsVector1ui;
  225. property AsVector2ui: TVector2ui read GetAsVector2ui write SetAsVector2ui;
  226. property AsVector3ui: TVector3ui read GetAsVector3ui write SetAsVector3ui;
  227. property AsVector4ui: TVector4ui read GetAsVector4ui write SetAsVector4ui;
  228. // Matrix Types.
  229. property AsMatrix2f: TMatrix2f read GetAsMatrix2f write SetAsMatrix2f;
  230. property AsMatrix3f: TMatrix3f read GetAsMatrix3f write SetAsMatrix3f;
  231. property AsMatrix4f: TMatrix4f read GetAsMatrix4f write SetAsMatrix4f;
  232. // Texture Types.
  233. property AsTexture [const TextureIndex: Integer]: TGLTexture write SetAsTexture;
  234. property AsTexture1D [const TextureIndex: Integer]: TGLTexture write SetAsTexture1D;
  235. property AsTexture2D [const TextureIndex: Integer]: TGLTexture write SetAsTexture2D;
  236. property AsTexture3D [const TextureIndex: Integer]: TGLTexture write SetAsTexture3D;
  237. property AsTextureRect[const TextureIndex: Integer]: TGLTexture write SetAsTextureRect;
  238. property AsTextureCube[const TextureIndex: Integer]: TGLTexture write SetAsTextureCube;
  239. property AsCustomTexture[const TextureIndex: Integer; TextureTarget: TGLTextureTarget]: Cardinal read GetAsCustomTexture write SetAsCustomTexture;
  240. property AsUniformBuffer: Cardinal read GetAsUniformBuffer write SetAsUniformBuffer;
  241. end;
  242. (* Adds two more blending modes to standard ones.
  243. Not sure how to name them or if they should be included in TBlending mode,
  244. so I created a new type here. *)
  245. TGLBlendingModeEx = (bmxOpaque, bmxTransparency, bmxAdditive,
  246. bmxAlphaTest50, bmxAlphaTest100, bmxModulate,
  247. bmxDestColorOne, bmxDestAlphaOne);
  248. // Exported procedures.
  249. procedure ApplyBlendingModeEx(const BlendingMode: TGLBlendingModeEx);
  250. procedure UnApplyBlendingModeEx;
  251. procedure InitTexture(
  252. const TextureHandle: Cardinal;
  253. const TextureSize: TGLSize;
  254. const TextureTarget: TGLTextureTarget = ttTexture2D);
  255. // Probably need to give them proper names, instead of numbers...
  256. procedure DrawTexturedScreenQuad;
  257. procedure DrawTexturedScreenQuad2(const ViewPortSize: TGLSize);
  258. procedure DrawTexturedScreenQuad3;
  259. procedure DrawTexturedScreenQuad4(const ViewPortSize: TGLSize);
  260. procedure DrawTexturedScreenQuad5(const ViewPortSize: TGLSize);
  261. procedure DrawTexturedScreenQuad6(const ViewPortSize: TGLSize);
  262. procedure CopyScreentoTexture(const ViewPortSize: TGLSize; const TextureTarget: Word = GL_TEXTURE_2D);
  263. procedure CopyScreentoTexture2(const ViewPortSize: TGLSize; const TextureTarget: Word = GL_TEXTURE_2D);
  264. function IsFogEnabled(const AFogSupportMode: TGLShaderFogSupport; var rci: TGLRenderContextInfo): Boolean;
  265. procedure GetActiveLightsList(const ALightIDs: TIntegerList);
  266. //------------------------------------------
  267. implementation
  268. //------------------------------------------
  269. uses
  270. GLState;
  271. procedure GetActiveLightsList(const ALightIDs: TIntegerList);
  272. var
  273. I: Integer;
  274. begin
  275. ALightIDs.Clear;
  276. with CurrentGLContext.GLStates do
  277. begin
  278. for I := 0 to MaxLights - 1 do
  279. begin
  280. if LightEnabling[I] then
  281. ALightIDs.Add(I);
  282. end;
  283. end;
  284. end;
  285. function IsFogEnabled(const AFogSupportMode: TGLShaderFogSupport; var rci: TGLRenderContextInfo): Boolean;
  286. begin
  287. case AFogSupportMode of
  288. sfsEnabled: Result := True;
  289. sfsDisabled: Result := False;
  290. sfsAuto: Result := TGLSceneBuffer(rci.buffer).FogEnable;
  291. else
  292. Result := False;
  293. Assert(False, strUnknownType);
  294. end;
  295. end;
  296. procedure CopyScreentoTexture(const ViewPortSize: TGLSize; const TextureTarget: Word = GL_TEXTURE_2D);
  297. begin
  298. gl.CopyTexSubImage2D(TextureTarget, 0, 0, 0, 0, 0, ViewPortSize.cx, ViewPortSize.cy);
  299. end;
  300. procedure CopyScreentoTexture2(const ViewPortSize: TGLSize; const TextureTarget: Word = GL_TEXTURE_2D);
  301. begin
  302. gl.CopyTexImage2D(TextureTarget, 0, GL_RGB, 0, 0, ViewPortSize.cx, ViewPortSize.cy, 0);
  303. end;
  304. procedure ApplyBlendingModeEx(const BlendingMode: TGLBlendingModeEx);
  305. begin
  306. with CurrentGLContext.GLStates do
  307. begin
  308. Enable(stBlend);
  309. case BlendingMode of
  310. bmxOpaque: SetBlendFunc(bfSRCALPHA, bfONE);
  311. bmxTransparency: SetBlendFunc(bfSRCALPHA, bfONEMINUSSRCALPHA);
  312. bmxAdditive: SetBlendFunc(bfSRCALPHA, bfONE);
  313. bmxAlphaTest50: SetGLAlphaFunction(cfGEQUAL, 0.5);
  314. bmxAlphaTest100: SetGLAlphaFunction(cfGEQUAL, 1.0);
  315. bmxModulate: SetBlendFunc(bfDSTCOLOR, bfZERO);
  316. bmxDestColorOne: SetBlendFunc(bfDSTCOLOR, bfONE);
  317. bmxDestAlphaOne: SetBlendFunc(bfDSTALPHA, bfONE);
  318. else
  319. Assert(False, strErrorEx + strUnknownType);
  320. end;
  321. end;
  322. end;
  323. procedure UnApplyBlendingModeEx;
  324. begin
  325. end;
  326. procedure DrawTexturedScreenQuad;
  327. begin
  328. gl.MatrixMode(GL_MODELVIEW);
  329. gl.PushMatrix;
  330. gl.LoadIdentity;
  331. gl.MatrixMode(GL_PROJECTION);
  332. gl.PushMatrix;
  333. gl.LoadIdentity;
  334. // drawing rectangle over screen
  335. gl.Disable(GL_DEPTH_TEST);
  336. DrawTexturedScreenQuad3;
  337. gl.Enable(GL_DEPTH_TEST);
  338. gl.PopMatrix;
  339. gl.MatrixMode(GL_MODELVIEW);
  340. gl.PopMatrix;
  341. end;
  342. procedure DrawTexturedScreenQuad2(const ViewPortSize: TGLSize);
  343. begin
  344. gl.PushMatrix;
  345. gl.MatrixMode(GL_PROJECTION);
  346. gl.PushMatrix;
  347. gl.LoadIdentity;
  348. gl.Ortho(0, ViewPortSize.cx, ViewPortSize.cy, 0, 0, 1);
  349. gl.Disable(GL_DEPTH_TEST);
  350. gl.DepthMask(False);
  351. gl.Begin_(GL_QUADS);
  352. gl.TexCoord2f(0.0, ViewPortSize.cy); gl.Vertex2f(0, 0);
  353. gl.TexCoord2f(0.0, 0.0); gl.Vertex2f(0, ViewPortSize.cy);
  354. gl.TexCoord2f(ViewPortSize.cx, 0.0); gl.Vertex2f(ViewPortSize.cx, ViewPortSize.cy);
  355. gl.TexCoord2f(ViewPortSize.cx, ViewPortSize.cy); gl.Vertex2f(ViewPortSize.cx, 0);
  356. gl.End_;
  357. gl.DepthMask(True);
  358. gl.Enable(GL_DEPTH_TEST);
  359. gl.MatrixMode(GL_PROJECTION);
  360. gl.PopMatrix;
  361. gl.MatrixMode(GL_MODELVIEW);
  362. gl.PopMatrix;
  363. end;
  364. procedure DrawTexturedScreenQuad4(const ViewPortSize: TGLSize);
  365. begin
  366. gl.Begin_(GL_QUADS);
  367. gl.TexCoord2f(0, 0); gl.Vertex2f(-1, -1);
  368. gl.TexCoord2f(ViewPortSize.cx, 0); gl.Vertex2f( 1, -1);
  369. gl.TexCoord2f(ViewPortSize.cx, ViewPortSize.cy); gl.Vertex2f( 1, 1);
  370. gl.TexCoord2f(0, ViewPortSize.cy); gl.Vertex2f(-1, 1);
  371. gl.End_;
  372. end;
  373. procedure DrawTexturedScreenQuad5(const ViewPortSize: TGLSize);
  374. begin
  375. gl.MatrixMode( GL_PROJECTION );
  376. gl.PushMatrix;
  377. gl.LoadIdentity;
  378. gl.Ortho( 0, ViewPortSize.cx, ViewPortSize.cy, 0, 0, 1 );
  379. gl.MatrixMode(GL_MODELVIEW);
  380. gl.PushMatrix;
  381. gl.LoadIdentity;
  382. gl.Disable(GL_DEPTH_TEST);
  383. gl.DepthMask( FALSE );
  384. DrawTexturedScreenQuad3;
  385. gl.DepthMask( TRUE );
  386. gl.Enable(GL_DEPTH_TEST);
  387. gl.PopMatrix;
  388. gl.MatrixMode( GL_PROJECTION );
  389. gl.PopMatrix;
  390. gl.MatrixMode( GL_MODELVIEW );
  391. end;
  392. procedure DrawTexturedScreenQuad6(const ViewPortSize: TGLSize);
  393. begin
  394. gl.MatrixMode( GL_PROJECTION );
  395. gl.PushMatrix;
  396. gl.LoadIdentity;
  397. gl.Ortho( 0, ViewPortSize.cx, ViewPortSize.cy, 0, 0, 1 );
  398. gl.MatrixMode(GL_MODELVIEW);
  399. gl.PushMatrix;
  400. gl.LoadIdentity;
  401. gl.Disable(GL_DEPTH_TEST);
  402. gl.DepthMask( FALSE );
  403. DrawTexturedScreenQuad4(ViewPortSize);;
  404. gl.DepthMask( TRUE );
  405. gl.Enable(GL_DEPTH_TEST);
  406. gl.PopMatrix;
  407. gl.MatrixMode( GL_PROJECTION );
  408. gl.PopMatrix;
  409. gl.MatrixMode( GL_MODELVIEW );
  410. end;
  411. procedure DrawTexturedScreenQuad3;
  412. begin
  413. gl.Begin_(GL_QUADS);
  414. gl.TexCoord2f(0, 0); gl.Vertex2f(-1, -1);
  415. gl.TexCoord2f(1, 0); gl.Vertex2f(1, -1);
  416. gl.TexCoord2f(1, 1); gl.Vertex2f(1, 1);
  417. gl.TexCoord2f(0, 1); gl.Vertex2f(-1, 1);
  418. gl.End_;
  419. end;
  420. procedure InitTexture(
  421. const TextureHandle: Cardinal;
  422. const TextureSize: TGLSize;
  423. const TextureTarget: TGLTextureTarget = ttTexture2D);
  424. var
  425. glTarget: Cardinal;
  426. begin
  427. with CurrentGLContext.GLStates do
  428. begin
  429. TextureBinding[ActiveTexture, TextureTarget] := TextureHandle;
  430. end;
  431. glTarget := DecodeTextureTarget(TextureTarget);
  432. gl.TexParameteri(glTarget, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
  433. gl.TexParameteri(glTarget, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
  434. gl.TexParameteri(glTarget, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
  435. gl.TexParameteri(glTarget, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  436. gl.CopyTexImage2D(glTarget, 0, GL_RGBA8, 0, 0, TextureSize.cx, TextureSize.cy, 0);
  437. end;
  438. { TGLShaderProgram }
  439. procedure TGLShaderProgram.Apply;
  440. begin
  441. FParent.FinalizeShader;
  442. end;
  443. procedure TGLShaderProgram.Assign(Source: TPersistent);
  444. begin
  445. if Source = nil then
  446. Exit;
  447. if (Source is TGLShaderProgram) then
  448. begin
  449. FEnabled := TGLShaderProgram(Source).FEnabled;
  450. FCode.Assign(TGLShaderProgram(Source).FCode);
  451. end
  452. else
  453. inherited; //die, die, die!!!
  454. end;
  455. constructor TGLShaderProgram.Create(const AParent: TGLCustomShader);
  456. begin
  457. FParent := AParent;
  458. FCode := TStringList.Create;
  459. TStringList(FCode).OnChange := OnChangeCode;
  460. FEnabled := False;
  461. end;
  462. destructor TGLShaderProgram.Destroy;
  463. begin
  464. FCode.Destroy;
  465. end;
  466. function TGLShaderProgram.GetOwner: TPersistent;
  467. begin
  468. Result := FParent;
  469. end;
  470. procedure TGLShaderProgram.LoadFromFile(const AFileName: string);
  471. begin
  472. FCode.LoadFromFile(AFileName);
  473. FEnabled := True;
  474. end;
  475. procedure TGLShaderProgram.OnChangeCode(Sender: TObject);
  476. begin
  477. FEnabled := True;
  478. FParent.NotifyChange(self);
  479. end;
  480. procedure TGLShaderProgram.SetCode(const Value: TStrings);
  481. begin
  482. FCode.Assign(Value);
  483. FParent.NotifyChange(self);
  484. end;
  485. procedure TGLShaderProgram.SetEnabled(const Value: Boolean);
  486. begin
  487. if Value = FEnabled then
  488. Exit;
  489. FEnabled := Value;
  490. if FEnabled then
  491. FParent.FinalizeShader;
  492. end;
  493. { TGLCustomShader }
  494. procedure TGLCustomShader.Assign(Source: TPersistent);
  495. begin
  496. if Source is TGLCustomShader then
  497. begin
  498. FFragmentProgram.Assign(TGLCustomShader(Source).FFragmentProgram);
  499. FVertexProgram.Assign(TGLCustomShader(Source).FVertexProgram);
  500. FGeometryProgram.Assign(TGLCustomShader(Source).FGeometryProgram);
  501. FTagObject := TGLCustomShader(Source).FTagObject;
  502. end;
  503. inherited;
  504. end;
  505. constructor TGLCustomShader.Create(AOwner: TComponent);
  506. begin
  507. inherited Create(AOwner);
  508. FDebugMode := False;
  509. FFragmentProgram := TGLFragmentProgram.Create(Self);
  510. FVertexProgram := TGLVertexProgram.Create(Self);
  511. FGeometryProgram := TGLGeometryProgram.Create(Self);
  512. end;
  513. destructor TGLCustomShader.Destroy;
  514. begin
  515. FFragmentProgram.Destroy;
  516. FVertexProgram.Destroy;
  517. FGeometryProgram.Destroy;
  518. inherited;
  519. end;
  520. procedure TGLCustomShader.LoadShaderPrograms(const VPFilename, FPFilename: string; const GPFilename: string = '');
  521. begin
  522. If VPFilename <> '' then VertexProgram.LoadFromFile(VPFilename);
  523. If FPFilename <> '' then FragmentProgram.LoadFromFile(FPFilename);
  524. If GPFilename <> '' then GeometryProgram.LoadFromFile(GPFilename);
  525. end;
  526. procedure TGLCustomShader.SetDebugMode(const Value: Boolean);
  527. begin
  528. if FDebugMode <> Value then
  529. begin
  530. FDebugMode := Value;
  531. if FDebugMode then
  532. FailedInitAction := fiaReRaiseException
  533. else
  534. FailedInitAction := fiaRaiseStandardException;
  535. end;
  536. end;
  537. procedure TGLCustomShader.SetFragmentProgram(const Value: TGLFragmentProgram);
  538. begin
  539. FFragmentProgram.Assign(Value);
  540. end;
  541. procedure TGLCustomShader.SetGeometryProgram(const Value: TGLGeometryProgram);
  542. begin
  543. FGeometryProgram.Assign(Value);
  544. end;
  545. procedure TGLCustomShader.SetVertexProgram(const Value: TGLVertexProgram);
  546. begin
  547. FVertexProgram.Assign(Value);
  548. end;
  549. function TGLCustomShader.StoreFragmentProgram: Boolean;
  550. begin
  551. Result := FFragmentProgram.Enabled or (FFragmentProgram.Code.Text <> '')
  552. end;
  553. function TGLCustomShader.StoreGeometryProgram: Boolean;
  554. begin
  555. Result := FGeometryProgram.Enabled or (FGeometryProgram.Code.Text <> '')
  556. end;
  557. function TGLCustomShader.StoreVertexProgram: Boolean;
  558. begin
  559. Result := FVertexProgram.Enabled or (FVertexProgram.Code.Text <> '')
  560. end;
  561. { TGLCustomShaderParameter }
  562. procedure TGLCustomShaderParameter.SetAsTexture(
  563. const TextureIndex: Integer; const Value: TGLTexture);
  564. begin
  565. SetAsCustomTexture(TextureIndex, Value.TextureHandle.Target, Value.Handle);
  566. end;
  567. procedure TGLCustomShaderParameter.SetAsTexture1D(
  568. const TextureIndex: Integer; const Value: TGLTexture);
  569. begin
  570. SetAsCustomTexture(TextureIndex, ttTexture1D, Value.Handle);
  571. end;
  572. procedure TGLCustomShaderParameter.SetAsTexture2D(
  573. const TextureIndex: Integer; const Value: TGLTexture);
  574. begin
  575. SetAsCustomTexture(TextureIndex, ttTexture2D, Value.Handle);
  576. end;
  577. procedure TGLCustomShaderParameter.SetAsTexture3D(
  578. const TextureIndex: Integer; const Value: TGLTexture);
  579. begin
  580. SetAsCustomTexture(TextureIndex, ttTexture3D, Value.Handle);
  581. end;
  582. procedure TGLCustomShaderParameter.SetAsTextureCube(
  583. const TextureIndex: Integer; const Value: TGLTexture);
  584. begin
  585. SetAsCustomTexture(TextureIndex, ttTextureCube, Value.Handle);
  586. end;
  587. procedure TGLCustomShaderParameter.SetAsTextureRect(
  588. const TextureIndex: Integer; const Value: TGLTexture);
  589. begin
  590. SetAsCustomTexture(TextureIndex, ttTextureRect, Value.Handle);
  591. end;
  592. procedure TGLCustomShaderParameter.SetAsVectorF(const Values: array of Single);
  593. begin
  594. case Length(Values) of
  595. 1: SetAsVector1f(Values[0]);
  596. 2: SetAsVector2f(Vector2fMake(Values[0], Values[1]));
  597. 3: SetAsVector3f(Vector3fMake(Values[0], Values[1], Values[2]));
  598. 4: SetAsVector4f(Vector4fMake(Values[0], Values[1], Values[2], Values[3]));
  599. else
  600. Assert(False, 'Vector length must be between 1 to 4');
  601. end;
  602. end;
  603. procedure TGLCustomShaderParameter.SetAsVectorI(const Values: array of Integer);
  604. begin
  605. case Length(Values) of
  606. 1: SetAsVector1i(Values[0]);
  607. 2: SetAsVector2i(Vector2iMake(Values[0], Values[1]));
  608. 3: SetAsVector3i(Vector3iMake(Values[0], Values[1], Values[2]));
  609. 4: SetAsVector4i(Vector4iMake(Values[0], Values[1], Values[2], Values[3]));
  610. else
  611. Assert(False, 'Vector length must be between 1 to 4');
  612. end;
  613. end;
  614. procedure TGLCustomShaderParameter.SetToTextureOf(
  615. const LibMaterial: TGLLibMaterial; const TextureIndex: Integer);
  616. begin
  617. SetToTextureOf(LibMaterial.Material.Texture, TextureIndex);
  618. end;
  619. procedure TGLCustomShaderParameter.SetToTextureOf(
  620. const Texture: TGLTexture; const TextureIndex: Integer);
  621. begin
  622. SetAsCustomTexture(TextureIndex, Texture.Image.NativeTextureTarget, Texture.Handle);
  623. end;
  624. constructor TGLGeometryProgram.Create(const AParent: TGLCustomShader);
  625. begin
  626. inherited Create(AParent);
  627. FInputPrimitiveType := gsInPoints;
  628. FOutputPrimitiveType := gsOutPoints;
  629. FVerticesOut := 0;
  630. end;
  631. procedure TGLGeometryProgram.SetInputPrimitiveType(const Value: TGLgsInTypes);
  632. begin
  633. if Value <> FInputPrimitiveType then
  634. begin
  635. FInputPrimitiveType := Value;
  636. FParent.NotifyChange(Self);
  637. end;
  638. end;
  639. procedure TGLGeometryProgram.SetOutputPrimitiveType(const Value: TGLgsOutTypes);
  640. begin
  641. if Value<>FOutputPrimitiveType then
  642. begin
  643. FOutputPrimitiveType := Value;
  644. FParent.NotifyChange(Self);
  645. end;
  646. end;
  647. procedure TGLGeometryProgram.SetVerticesOut(const Value: TGLint);
  648. begin
  649. if Value<>FVerticesOut then
  650. begin
  651. FVerticesOut := Value;
  652. FParent.NotifyChange(Self);
  653. end;
  654. end;
  655. initialization
  656. RegisterClasses([TGLCustomShader, TGLShaderProgram,
  657. TGLVertexProgram, TGLFragmentProgram, TGLGeometryProgram]);
  658. end.