GLS.XOpenGL.pas 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866
  1. //
  2. // The multimedia graphics platform GLScene https://github.com/glscene
  3. //
  4. unit GLS.XOpenGL;
  5. (*
  6. "Alternate" OpenGL functions to handle multi-texturing.
  7. Using this functions allows specifying none/one/multiple ARB multi-texture
  8. coordinates with standard texture specification call.
  9. Before using any of the xglTexCoordXxxx fonctions, call one of the
  10. xglMapTexCoordToXxxx functions to establish the redirectors.
  11. *)
  12. interface
  13. {$I GLScene.inc}
  14. uses
  15. Winapi.OpenGLext,
  16. GLS.VectorTypes,
  17. GLS.OpenGLTokens,
  18. GLS.State;
  19. type
  20. TMapTexCoordMode = (mtcmUndefined, mtcmNull, mtcmMain, mtcmDual, mtcmSecond,
  21. mtcmArbitrary);
  22. TGLMultitextureCoordinator = class
  23. private
  24. FMapTexCoordMode: TMapTexCoordMode;
  25. FSecondTextureUnitForbidden: Boolean;
  26. FUpdCount: Integer;
  27. FUpdNewMode: TMapTexCoordMode;
  28. FStateStack: array of TMapTexCoordMode;
  29. FComplexMapping: array of Cardinal;
  30. FComplexMappingN: Integer;
  31. public
  32. // Explicit texture coordinates specification
  33. TexCoord2f: procedure(s, t: TGLfloat);stdcall;
  34. TexCoord2fv: procedure(v: PGLfloat);stdcall;
  35. TexCoord3f: procedure(s, t, r: TGLfloat);stdcall;
  36. TexCoord3fv: procedure(v: PGLfloat);stdcall;
  37. TexCoord4f: procedure(s, t, r, q: TGLfloat);stdcall;
  38. TexCoord4fv: procedure(v: PGLfloat);stdcall;
  39. // TexGen texture coordinates specification
  40. TexGenf: procedure(coord, pname: Cardinal; param: TGLfloat);stdcall;
  41. TexGenfv: procedure(coord, pname: Cardinal; params: PGLfloat);stdcall;
  42. TexGeni: procedure(coord, pname: Cardinal; param: TGLint);stdcall;
  43. TexGeniv: procedure(coord, pname: Cardinal; params: PGLint);stdcall;
  44. // Vertex Arrays texture coordinates specification
  45. TexCoordPointer: procedure(size: TGLint; atype: Cardinal; stride: TGLsizei; data: pointer);stdcall;
  46. EnableClientState: procedure(aarray: Cardinal);stdcall;
  47. DisableClientState: procedure(aarray: Cardinal);stdcall;
  48. // Misc
  49. Enable: procedure(cap: Cardinal);stdcall;
  50. Disable: procedure(cap: Cardinal);stdcall;
  51. constructor Create;
  52. // TexCoord functions will be ignored.
  53. procedure MapTexCoordToNull;
  54. // TexCoord functions will define the main texture coordinates.
  55. procedure MapTexCoordToMain;
  56. // TexCoord functions will define the second texture unit coordinates.
  57. procedure MapTexCoordToSecond;
  58. // TexCoord functions will define the two first texture units coordinates.
  59. procedure MapTexCoordToDual;
  60. // TexCoord functions will define the specified texture units coordinates.
  61. procedure MapTexCoordToArbitrary(const units: array of Cardinal); overload;
  62. procedure MapTexCoordToArbitrary(const bitWiseUnits: Cardinal); overload;
  63. procedure MapTexCoordToArbitraryAdd(const bitWiseUnits: Cardinal);
  64. (* Defers Map calls execution until EndUpdate is met.
  65. Calls to Begin/EndUpdate may be nested. *)
  66. procedure BeginUpdate; inline;
  67. (* Applies Map calls if there were any since BeginUpdate was invoked.
  68. Calls to Begin/EndUpdate may be nested. *)
  69. procedure EndUpdate; inline;
  70. // Saves XOpenGL State on the stack.
  71. procedure PushState;
  72. // Restores XOpenGL State from the stack.
  73. procedure PopState;
  74. (* Whenever called, 2nd texture units changes will be forbidden to .
  75. Use this function when you're using the 2nd texture unit for your own
  76. purposes and don't want XOpenGL to alter it. *)
  77. procedure ForbidSecondTextureUnit;
  78. // Allow XOpenGL to use the second texture unit again.
  79. procedure AllowSecondTextureUnit;
  80. // Returns the complex mapping in bitwise form.
  81. function GetBitWiseMapping: Cardinal;
  82. property MapTexCoordMode: TMapTexCoordMode read FMapTexCoordMode write FMapTexCoordMode;
  83. property SecondTextureUnitForbidden: Boolean read FSecondTextureUnitForbidden;
  84. end;
  85. // ------------------------------------------------------------------
  86. implementation
  87. // ------------------------------------------------------------------
  88. uses
  89. GLS.Context;
  90. // ------------------------------------------------------------------
  91. // Multitexturing coordinates duplication functions
  92. // ------------------------------------------------------------------
  93. // --------- Complex (arbitrary) mapping
  94. procedure TexCoord2f_Arbitrary(s, t: TGLfloat);stdcall;
  95. var
  96. i: Integer;
  97. begin
  98. for i := 0 to xgl.FComplexMappingN do
  99. gl.MultiTexCoord2f(xgl.FComplexMapping[i], s, t);
  100. end;
  101. procedure TexCoord2fv_Arbitrary(v: PGLfloat);stdcall;
  102. var
  103. i: Integer;
  104. begin
  105. for i := 0 to xgl.FComplexMappingN do
  106. gl.MultiTexCoord2fv(xgl.FComplexMapping[i], v);
  107. end;
  108. procedure TexCoord3f_Arbitrary(s, t, r: TGLfloat);stdcall;
  109. var
  110. i: Integer;
  111. begin
  112. for i := 0 to xgl.FComplexMappingN do
  113. gl.MultiTexCoord3f(xgl.FComplexMapping[i], s, t, r);
  114. end;
  115. procedure TexCoord3fv_Arbitrary(v: PGLfloat);stdcall;
  116. var
  117. i: Integer;
  118. begin
  119. for i := 0 to xgl.FComplexMappingN do
  120. gl.MultiTexCoord3fv(xgl.FComplexMapping[i], v);
  121. end;
  122. procedure TexCoord4f_Arbitrary(s, t, r, q: TGLfloat);stdcall;
  123. var
  124. i: Integer;
  125. begin
  126. for i := 0 to xgl.FComplexMappingN do
  127. gl.MultiTexCoord4f(xgl.FComplexMapping[i], s, t, r, q);
  128. end;
  129. procedure TexCoord4fv_Arbitrary(v: PGLfloat);stdcall;
  130. var
  131. i: Integer;
  132. begin
  133. for i := 0 to xgl.FComplexMappingN do
  134. gl.MultiTexCoord4fv(xgl.FComplexMapping[i], v);
  135. end;
  136. procedure TexGenf_Arbitrary(coord, pname: Cardinal; param: TGLfloat);stdcall;
  137. var
  138. i: Integer;
  139. begin
  140. for i := 0 to xgl.FComplexMappingN do
  141. begin
  142. CurrentGLContext.GLStates.ActiveTexture := xgl.FComplexMapping[i];
  143. gl.TexGenf(coord, pname, param);
  144. end;
  145. end;
  146. procedure TexGenfv_Arbitrary(coord, pname: Cardinal; params: PGLfloat);stdcall;
  147. var
  148. i: Integer;
  149. begin
  150. for i := 0 to xgl.FComplexMappingN do
  151. begin
  152. CurrentGLContext.GLStates.ActiveTexture := xgl.FComplexMapping[i];
  153. gl.TexGenfv(coord, pname, params);
  154. end;
  155. end;
  156. procedure TexGeni_Arbitrary(coord, pname: Cardinal; param: TGLint);stdcall;
  157. var
  158. i: Integer;
  159. begin
  160. for i := 0 to xgl.FComplexMappingN do
  161. begin
  162. CurrentGLContext.GLStates.ActiveTexture := xgl.FComplexMapping[i];
  163. gl.TexGeni(coord, pname, param);
  164. end;
  165. end;
  166. procedure TexGeniv_Arbitrary(coord, pname: Cardinal; params: PGLint);stdcall;
  167. var
  168. i: Integer;
  169. begin
  170. for i := 0 to xgl.FComplexMappingN do
  171. begin
  172. CurrentGLContext.GLStates.ActiveTexture := xgl.FComplexMapping[i];
  173. gl.TexGeniv(coord, pname, params);
  174. end;
  175. end;
  176. procedure Enable_Arbitrary(cap: Cardinal);stdcall;
  177. var
  178. i: Integer;
  179. begin
  180. for i := 0 to xgl.FComplexMappingN do
  181. begin
  182. CurrentGLContext.GLStates.ActiveTexture := xgl.FComplexMapping[i];
  183. gl.Enable(cap);
  184. end;
  185. end;
  186. procedure Disable_Arbitrary(cap: Cardinal);stdcall;
  187. var
  188. i: Integer;
  189. begin
  190. for i := 0 to xgl.FComplexMappingN do
  191. begin
  192. CurrentGLContext.GLStates.ActiveTexture := xgl.FComplexMapping[i];
  193. gl.Disable(cap);
  194. end;
  195. end;
  196. procedure TexCoordPointer_Arbitrary(size: TGLint; atype: Cardinal; stride: TGLsizei; data: pointer);
  197. stdcall;
  198. var
  199. i: Integer;
  200. begin
  201. for i := 0 to xgl.FComplexMappingN do
  202. begin
  203. gl.ClientActiveTexture(xgl.FComplexMapping[i]);
  204. gl.TexCoordPointer(size, atype, stride, data);
  205. end;
  206. end;
  207. procedure EnableClientState_Arbitrary(aArray: Cardinal);stdcall;
  208. var
  209. i: Integer;
  210. begin
  211. for i := 0 to xgl.FComplexMappingN do
  212. begin
  213. gl.ClientActiveTexture(xgl.FComplexMapping[i]);
  214. gl.EnableClientState(aArray);
  215. end;
  216. end;
  217. procedure DisableClientState_Arbitrary(aArray: Cardinal);stdcall;
  218. var
  219. i: Integer;
  220. begin
  221. for i := 0 to xgl.FComplexMappingN do
  222. begin
  223. gl.ClientActiveTexture(xgl.FComplexMapping[i]);
  224. gl.DisableClientState(aArray);
  225. end;
  226. end;
  227. // --------- Second unit Texturing
  228. procedure TexCoord2f_Second(s, t: TGLfloat);stdcall;
  229. begin
  230. gl.MultiTexCoord2f(GL_TEXTURE1, s, t);
  231. end;
  232. procedure TexCoord2fv_Second(v: PGLfloat);stdcall;
  233. begin
  234. gl.MultiTexCoord2fv(GL_TEXTURE1, v);
  235. end;
  236. procedure TexCoord3f_Second(s, t, r: TGLfloat);stdcall;
  237. begin
  238. gl.MultiTexCoord3f(GL_TEXTURE1, s, t, r);
  239. end;
  240. procedure TexCoord3fv_Second(v: PGLfloat);stdcall;
  241. begin
  242. gl.MultiTexCoord3fv(GL_TEXTURE1, v);
  243. end;
  244. procedure TexCoord4f_Second(s, t, r, q: TGLfloat);stdcall;
  245. begin
  246. gl.MultiTexCoord4f(GL_TEXTURE1, s, t, r, q);
  247. end;
  248. procedure TexCoord4fv_Second(v: PGLfloat);stdcall;
  249. begin
  250. gl.MultiTexCoord4fv(GL_TEXTURE1, v);
  251. end;
  252. procedure TexGenf_Second(coord, pname: Cardinal; param: TGLfloat);stdcall;
  253. begin
  254. CurrentGLContext.GLStates.ActiveTexture := 1;
  255. gl.TexGenf(coord, pname, param);
  256. end;
  257. procedure TexGenfv_Second(coord, pname: Cardinal; params: PGLfloat);stdcall;
  258. begin
  259. CurrentGLContext.GLStates.ActiveTexture := 1;
  260. gl.TexGenfv(coord, pname, params);
  261. end;
  262. procedure TexGeni_Second(coord, pname: Cardinal; param: TGLint);stdcall;
  263. begin
  264. CurrentGLContext.GLStates.ActiveTexture := 1;
  265. gl.TexGeni(coord, pname, param);
  266. end;
  267. procedure TexGeniv_Second(coord, pname: Cardinal; params: PGLint);stdcall;
  268. begin
  269. CurrentGLContext.GLStates.ActiveTexture := 1;
  270. gl.TexGeniv(coord, pname, params);
  271. end;
  272. procedure Enable_Second(cap: Cardinal);stdcall;
  273. begin
  274. CurrentGLContext.GLStates.ActiveTexture := 1;
  275. gl.Enable(cap);
  276. end;
  277. procedure Disable_Second(cap: Cardinal);stdcall;
  278. begin
  279. CurrentGLContext.GLStates.ActiveTexture := 1;
  280. gl.Disable(cap);
  281. end;
  282. procedure TexCoordPointer_Second(size: TGLint; atype: Cardinal; stride:
  283. TGLsizei; data: pointer);stdcall;
  284. begin
  285. gl.ClientActiveTexture(GL_TEXTURE1);
  286. gl.TexCoordPointer(size, atype, stride, data);
  287. gl.ClientActiveTexture(GL_TEXTURE0);
  288. end;
  289. procedure EnableClientState_Second(aArray: Cardinal);stdcall;
  290. begin
  291. gl.ClientActiveTexture(GL_TEXTURE1);
  292. gl.EnableClientState(aArray);
  293. gl.ClientActiveTexture(GL_TEXTURE0);
  294. end;
  295. procedure DisableClientState_Second(aArray: Cardinal);stdcall;
  296. begin
  297. gl.ClientActiveTexture(GL_TEXTURE1);
  298. gl.DisableClientState(aArray);
  299. gl.ClientActiveTexture(GL_TEXTURE0);
  300. end;
  301. // --------- Dual Texturing
  302. procedure TexCoord2f_Dual(s, t: TGLfloat);stdcall;
  303. begin
  304. gl.TexCoord2f(s, t);
  305. gl.MultiTexCoord2f(GL_TEXTURE1, s, t);
  306. end;
  307. procedure TexCoord2fv_Dual(v: PGLfloat);stdcall;
  308. begin
  309. gl.TexCoord2fv(v);
  310. gl.MultiTexCoord2fv(GL_TEXTURE1, v);
  311. end;
  312. procedure TexCoord3f_Dual(s, t, r: TGLfloat);stdcall;
  313. begin
  314. gl.TexCoord3f(s, t, r);
  315. gl.MultiTexCoord3f(GL_TEXTURE1, s, t, r);
  316. end;
  317. procedure TexCoord3fv_Dual(v: PGLfloat);stdcall;
  318. begin
  319. gl.TexCoord3fv(v);
  320. gl.MultiTexCoord3fv(GL_TEXTURE1, v);
  321. end;
  322. procedure TexCoord4f_Dual(s, t, r, q: TGLfloat);stdcall;
  323. begin
  324. gl.TexCoord4f(s, t, r, q);
  325. gl.MultiTexCoord4f(GL_TEXTURE1, s, t, r, q);
  326. end;
  327. procedure TexCoord4fv_Dual(v: PGLfloat);stdcall;
  328. begin
  329. gl.TexCoord4fv(v);
  330. gl.MultiTexCoord4fv(GL_TEXTURE1, v);
  331. end;
  332. procedure TexGenf_Dual(coord, pname: Cardinal; param: TGLfloat);stdcall;
  333. begin
  334. with CurrentGLContext.GLStates do
  335. begin
  336. ActiveTexture := 0;
  337. gl.TexGenf(coord, pname, param);
  338. ActiveTexture := 1;
  339. gl.TexGenf(coord, pname, param);
  340. end;
  341. end;
  342. procedure TexGenfv_Dual(coord, pname: Cardinal; params: PGLfloat);
  343. stdcall;
  344. begin
  345. with CurrentGLContext.GLStates do
  346. begin
  347. ActiveTexture := 0;
  348. gl.TexGenfv(coord, pname, params);
  349. ActiveTexture := 1;
  350. gl.TexGenfv(coord, pname, params);
  351. end;
  352. end;
  353. procedure TexGeni_Dual(coord, pname: Cardinal; param: TGLint);stdcall;
  354. begin
  355. with CurrentGLContext.GLStates do
  356. begin
  357. ActiveTexture := 0;
  358. gl.TexGeni(coord, pname, param);
  359. ActiveTexture := 1;
  360. gl.TexGeni(coord, pname, param);
  361. end;
  362. end;
  363. procedure TexGeniv_Dual(coord, pname: Cardinal; params: PGLint);stdcall;
  364. begin
  365. with CurrentGLContext.GLStates do
  366. begin
  367. ActiveTexture := 0;
  368. gl.TexGeniv(coord, pname, params);
  369. ActiveTexture := 1;
  370. gl.TexGeniv(coord, pname, params);
  371. end;
  372. end;
  373. procedure Enable_Dual(cap: Cardinal);stdcall;
  374. begin
  375. with CurrentGLContext.GLStates do
  376. begin
  377. ActiveTexture := 0;
  378. gl.Enable(cap);
  379. ActiveTexture := 1;
  380. gl.Enable(cap);
  381. end;
  382. end;
  383. procedure Disable_Dual(cap: Cardinal);stdcall;
  384. begin
  385. with CurrentGLContext.GLStates do
  386. begin
  387. ActiveTexture := 0;
  388. gl.Disable(cap);
  389. ActiveTexture := 1;
  390. gl.Disable(cap);
  391. end;
  392. end;
  393. procedure TexCoordPointer_Dual(size: TGLint; atype: Cardinal; stride:
  394. TGLsizei; data: pointer);stdcall;
  395. begin
  396. gl.TexCoordPointer(size, atype, stride, data);
  397. gl.ClientActiveTexture(GL_TEXTURE1);
  398. gl.TexCoordPointer(size, atype, stride, data);
  399. gl.ClientActiveTexture(GL_TEXTURE0);
  400. end;
  401. procedure EnableClientState_Dual(aArray: Cardinal);stdcall;
  402. begin
  403. gl.EnableClientState(aArray);
  404. gl.ClientActiveTexture(GL_TEXTURE1);
  405. gl.EnableClientState(aArray);
  406. gl.ClientActiveTexture(GL_TEXTURE0);
  407. end;
  408. procedure DisableClientState_Dual(aArray: Cardinal);stdcall;
  409. begin
  410. gl.DisableClientState(aArray);
  411. gl.ClientActiveTexture(GL_TEXTURE1);
  412. gl.DisableClientState(aArray);
  413. gl.ClientActiveTexture(GL_TEXTURE0);
  414. end;
  415. // --------- Null Texturing
  416. procedure TexCoord2f_Null(s, t: TGLfloat);stdcall;
  417. begin
  418. end;
  419. procedure TexCoord2fv_Null(v: PGLfloat);stdcall;
  420. begin
  421. end;
  422. procedure TexCoord3f_Null(s, t, r: TGLfloat);stdcall;
  423. begin
  424. end;
  425. procedure TexCoord3fv_Null(v: PGLfloat);stdcall;
  426. begin
  427. end;
  428. procedure TexCoord4f_Null(s, t, r, q: TGLfloat);stdcall;
  429. begin
  430. end;
  431. procedure TexCoord4fv_Null(v: PGLfloat);stdcall;
  432. begin
  433. end;
  434. procedure TexGenf_Null(coord, pname: Cardinal; param: TGLfloat);stdcall;
  435. begin
  436. end;
  437. procedure TexGenfv_Null(coord, pname: Cardinal; params: PGLfloat);stdcall;
  438. begin
  439. end;
  440. procedure TexGeni_Null(coord, pname: Cardinal; param: TGLint);stdcall;
  441. begin
  442. end;
  443. procedure TexGeniv_Null(coord, pname: Cardinal; params: PGLint);stdcall;
  444. begin
  445. end;
  446. procedure Enable_Null(cap: Cardinal);stdcall;
  447. begin
  448. end;
  449. procedure Disable_Null(cap: Cardinal);stdcall;
  450. begin
  451. end;
  452. procedure TexCoordPointer_Null(size: TGLint; atype: Cardinal; stride: TGLsizei; data: pointer);stdcall;
  453. begin
  454. end;
  455. procedure EnableClientState_Null(aArray: Cardinal);stdcall;
  456. begin
  457. end;
  458. procedure DisableClientState_Null(aArray: Cardinal);stdcall;
  459. begin
  460. end;
  461. // ------------------------------------------------------------------
  462. // Redirections management functions
  463. // ------------------------------------------------------------------
  464. procedure TGLMultitextureCoordinator.BeginUpdate;
  465. begin
  466. if FUpdCount = 0 then
  467. begin
  468. FUpdCount := 1;
  469. FUpdNewMode := MapTexCoordMode;
  470. end
  471. else
  472. Inc(FUpdCount);
  473. end;
  474. procedure TGLMultitextureCoordinator.EndUpdate;
  475. begin
  476. Dec(FUpdCount);
  477. if (FUpdCount = 0) and (FUpdNewMode <> MapTexCoordMode) then
  478. begin
  479. case FUpdNewMode of
  480. mtcmNull: MapTexCoordToNull;
  481. mtcmMain: MapTexCoordToMain;
  482. mtcmDual: MapTexCoordToDual;
  483. mtcmSecond: MapTexCoordToSecond;
  484. mtcmArbitrary: MapTexCoordToArbitrary(FComplexMapping);
  485. else
  486. Assert(False);
  487. end;
  488. end;
  489. end;
  490. procedure TGLMultitextureCoordinator.PushState;
  491. var
  492. i: Integer;
  493. begin
  494. Assert(FUpdCount = 0);
  495. i := Length(FStateStack);
  496. SetLength(FStateStack, i + 1);
  497. FStateStack[i] := MapTexCoordMode;
  498. end;
  499. procedure TGLMultitextureCoordinator.PopState;
  500. var
  501. i: Integer;
  502. begin
  503. Assert(FUpdCount = 0);
  504. i := Length(FStateStack) - 1;
  505. Assert(i >= 0);
  506. case FStateStack[i] of
  507. mtcmNull: MapTexCoordToNull;
  508. mtcmMain: MapTexCoordToMain;
  509. mtcmDual: MapTexCoordToDual;
  510. mtcmSecond: MapTexCoordToSecond;
  511. mtcmArbitrary: MapTexCoordToArbitrary(FComplexMapping);
  512. else
  513. Assert(False);
  514. end;
  515. SetLength(FStateStack, i);
  516. end;
  517. procedure TGLMultitextureCoordinator.ForbidSecondTextureUnit;
  518. begin
  519. FSecondTextureUnitForbidden := True;
  520. end;
  521. procedure TGLMultitextureCoordinator.AllowSecondTextureUnit;
  522. begin
  523. FSecondTextureUnitForbidden := False;
  524. end;
  525. constructor TGLMultitextureCoordinator.Create;
  526. begin
  527. inherited;
  528. FMapTexCoordMode := mtcmUndefined;
  529. MapTexCoordToNull;
  530. end;
  531. procedure TGLMultitextureCoordinator.MapTexCoordToNull;
  532. begin
  533. if FUpdCount <> 0 then
  534. FUpdNewMode := mtcmNull
  535. else if MapTexCoordMode <> mtcmNull then
  536. begin
  537. MapTexCoordMode := mtcmNull;
  538. TexCoord2f := TexCoord2f_Null;
  539. TexCoord2fv := TexCoord2fv_Null;
  540. TexCoord3f := TexCoord3f_Null;
  541. TexCoord3fv := TexCoord3fv_Null;
  542. TexCoord4f := TexCoord4f_Null;
  543. TexCoord4fv := TexCoord4fv_Null;
  544. TexGenf := TexGenf_Null;
  545. TexGenfv := TexGenfv_Null;
  546. TexGeni := TexGeni_Null;
  547. TexGeniv := TexGeniv_Null;
  548. TexCoordPointer := TexCoordPointer_Null;
  549. EnableClientState := EnableClientState_Null;
  550. DisableClientState := DisableClientState_Null;
  551. Enable := Enable_Null;
  552. Disable := Disable_Null;
  553. end;
  554. end;
  555. procedure TGLMultitextureCoordinator.MapTexCoordToMain;
  556. begin
  557. if FUpdCount <> 0 then
  558. FUpdNewMode := mtcmMain
  559. else if MapTexCoordMode <> mtcmMain then
  560. begin
  561. MapTexCoordMode := mtcmMain;
  562. TexCoord2f := gl.TexCoord2f;
  563. TexCoord2fv := gl.TexCoord2fv;
  564. TexCoord3f := gl.TexCoord3f;
  565. TexCoord3fv := gl.TexCoord3fv;
  566. TexCoord4f := gl.TexCoord4f;
  567. TexCoord4fv := gl.TexCoord4fv;
  568. TexGenf := gl.TexGenf;
  569. TexGenfv := gl.TexGenfv;
  570. TexGeni := gl.TexGeni;
  571. TexGeniv := gl.TexGeniv;
  572. TexCoordPointer := gl.TexCoordPointer;
  573. EnableClientState := gl.EnableClientState;
  574. DisableClientState := gl.DisableClientState;
  575. Enable := gl.Enable;
  576. Disable := gl.Disable;
  577. end;
  578. end;
  579. procedure TGLMultitextureCoordinator.MapTexCoordToSecond;
  580. begin
  581. if FSecondTextureUnitForbidden then
  582. begin
  583. MapTexCoordToNull;
  584. Exit;
  585. end;
  586. if FUpdCount <> 0 then
  587. FUpdNewMode := mtcmSecond
  588. else if MapTexCoordMode <> mtcmSecond then
  589. begin
  590. MapTexCoordMode := mtcmSecond;
  591. Assert(gl.ARB_multitexture);
  592. TexCoord2f := TexCoord2f_Second;
  593. TexCoord2fv := TexCoord2fv_Second;
  594. TexCoord3f := TexCoord3f_Second;
  595. TexCoord3fv := TexCoord3fv_Second;
  596. TexCoord4f := TexCoord4f_Second;
  597. TexCoord4fv := TexCoord4fv_Second;
  598. TexGenf := TexGenf_Second;
  599. TexGenfv := TexGenfv_Second;
  600. TexGeni := TexGeni_Second;
  601. TexGeniv := TexGeniv_Second;
  602. TexCoordPointer := TexCoordPointer_Second;
  603. EnableClientState := EnableClientState_Second;
  604. DisableClientState := DisableClientState_Second;
  605. Enable := Enable_Second;
  606. Disable := Disable_Second;
  607. end;
  608. end;
  609. procedure TGLMultitextureCoordinator.MapTexCoordToDual;
  610. begin
  611. if FSecondTextureUnitForbidden then
  612. begin
  613. MapTexCoordToMain;
  614. Exit;
  615. end;
  616. if FUpdCount <> 0 then
  617. FUpdNewMode := mtcmDual
  618. else if MapTexCoordMode <> mtcmDual then
  619. begin
  620. MapTexCoordMode := mtcmDual;
  621. Assert(GL.ARB_multitexture);
  622. TexCoord2f := TexCoord2f_Dual;
  623. TexCoord2fv := TexCoord2fv_Dual;
  624. TexCoord3f := TexCoord3f_Dual;
  625. TexCoord3fv := TexCoord3fv_Dual;
  626. TexCoord4f := TexCoord4f_Dual;
  627. TexCoord4fv := TexCoord4fv_Dual;
  628. TexGenf := TexGenf_Dual;
  629. TexGenfv := TexGenfv_Dual;
  630. TexGeni := TexGeni_Dual;
  631. TexGeniv := TexGeniv_Dual;
  632. TexCoordPointer := TexCoordPointer_Dual;
  633. EnableClientState := EnableClientState_Dual;
  634. DisableClientState := DisableClientState_Dual;
  635. Enable := Enable_Dual;
  636. Disable := Disable_Dual;
  637. end;
  638. end;
  639. procedure TGLMultitextureCoordinator.MapTexCoordToArbitrary(const units: array of Cardinal);
  640. var
  641. i, j, n: Integer;
  642. begin
  643. n := Length(units);
  644. SetLength(FComplexMapping, n);
  645. j := 0;
  646. FComplexMappingN := n - 1;
  647. for i := 0 to FComplexMappingN do
  648. begin
  649. if (not FSecondTextureUnitForbidden) or (units[i] <> GL_TEXTURE1) then
  650. begin
  651. FComplexMapping[j] := units[i];
  652. Inc(j);
  653. end;
  654. end;
  655. if FUpdCount <> 0 then
  656. FUpdNewMode := mtcmArbitrary
  657. else if MapTexCoordMode <> mtcmArbitrary then
  658. begin
  659. MapTexCoordMode := mtcmArbitrary;
  660. Assert(GL.ARB_multitexture);
  661. TexCoord2f := TexCoord2f_Arbitrary;
  662. TexCoord2fv := TexCoord2fv_Arbitrary;
  663. TexCoord3f := TexCoord3f_Arbitrary;
  664. TexCoord3fv := TexCoord3fv_Arbitrary;
  665. TexCoord4f := TexCoord4f_Arbitrary;
  666. TexCoord4fv := TexCoord4fv_Arbitrary;
  667. TexGenf := TexGenf_Arbitrary;
  668. TexGenfv := TexGenfv_Arbitrary;
  669. TexGeni := TexGeni_Arbitrary;
  670. TexGeniv := TexGeniv_Arbitrary;
  671. TexCoordPointer := TexCoordPointer_Arbitrary;
  672. EnableClientState := EnableClientState_Arbitrary;
  673. DisableClientState := DisableClientState_Arbitrary;
  674. Enable := Enable_Arbitrary;
  675. Disable := Disable_Arbitrary;
  676. end;
  677. end;
  678. procedure TGLMultitextureCoordinator.MapTexCoordToArbitrary(const bitWiseUnits: Cardinal);
  679. var
  680. i, n: Integer;
  681. units: array of Cardinal;
  682. begin
  683. n := 0;
  684. for i := 0 to 7 do
  685. begin
  686. if (bitWiseUnits and (1 shl i)) <> 0 then
  687. Inc(n);
  688. end;
  689. SetLength(units, n);
  690. n := 0;
  691. for i := 0 to 7 do
  692. begin
  693. if (bitWiseUnits and (1 shl i)) <> 0 then
  694. begin
  695. units[n] := GL_TEXTURE0 + i;
  696. Inc(n);
  697. end;
  698. end;
  699. MapTexCoordToArbitrary(units);
  700. end;
  701. procedure TGLMultitextureCoordinator.MapTexCoordToArbitraryAdd(const bitWiseUnits: Cardinal);
  702. var
  703. n: Cardinal;
  704. begin
  705. n := GetBitWiseMapping;
  706. MapTexCoordToArbitrary(n or bitWiseUnits);
  707. end;
  708. function TGLMultitextureCoordinator.GetBitWiseMapping: Cardinal;
  709. var
  710. i, n: Cardinal;
  711. mode: TMapTexCoordMode;
  712. begin
  713. if FUpdCount > 0 then
  714. mode := FUpdNewMode
  715. else
  716. mode := MapTexCoordMode;
  717. n := 0;
  718. case mode of
  719. mtcmMain: n := 1;
  720. mtcmDual: n := 3;
  721. mtcmSecond: n := 2;
  722. mtcmArbitrary:
  723. begin
  724. for i := 0 to FComplexMappingN do
  725. n := n or (1 shl (FComplexMapping[i] - GL_TEXTURE0));
  726. end;
  727. else
  728. Assert(False);
  729. end;
  730. Result := n;
  731. end;
  732. // ------------------------------------------------------------------------
  733. initialization
  734. // ------------------------------------------------------------------------
  735. end.