GLS.State.pas 118 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430343134323433343434353436343734383439344034413442344334443445344634473448344934503451345234533454345534563457345834593460346134623463346434653466346734683469347034713472347334743475347634773478347934803481348234833484348534863487348834893490349134923493349434953496349734983499350035013502350335043505350635073508350935103511351235133514351535163517
  1. //
  2. // The graphics engine GLScene
  3. //
  4. unit GLS.State;
  5. (* Tools for managing an application-side cache of OpenGL state. *)
  6. (*
  7. TODO: Proper client-side pushing + popping of state, in OpenGL 3+ contexts,
  8. rather than using glPushAttrib + glPopAttrib.
  9. TODO: Proper support for textures, taking into account that they probably
  10. won't be linked to texture units in some future version of OpenGL.
  11. TODO: Once more of GLScene is cache-aware, enable some of the checks before
  12. changing OpenGL state (where we will gain a speed increase).
  13. DONE: Cache some relevant legacy state
  14. TODO: improve binding objects to binding points
  15. TODO: decide how to implement the new Enable* options (without going above
  16. 32 elements in sets if possible, which would be slower in 32bit Delphi)
  17. DONE: remove stTexture1D, 2D, etc from TGLState if possible, since they are
  18. per texture-unit + also deprecated in OpenGL 3+
  19. *)
  20. interface
  21. {$I Stage.Defines.inc}
  22. { .$DEFINE USE_CACHE_MISS_CHECK }
  23. uses
  24. Winapi.OpenGL,
  25. Winapi.OpenGLext,
  26. System.Classes,
  27. System.SysUtils,
  28. Stage.OpenGLTokens,
  29. Stage.VectorTypes,
  30. Stage.VectorGeometry,
  31. Stage.TextureFormat,
  32. Stage.Utils,
  33. GLS.Color;
  34. const
  35. GLS_VERTEX_ATTR_NUM = 16;
  36. type
  37. TGLStateType = (sttCurrent, sttPoint, sttLine, sttPolygon, sttPolygonStipple,
  38. sttPixelMode, sttLighting, sttFog, sttDepthBuffer, sttAccumBuffer,
  39. sttStencilBuffer, sttViewport, sttTransform, sttEnable, sttColorBuffer,
  40. sttHint, sttEval, sttList, sttTexture, sttScissor,
  41. sttMultisample);
  42. TGLStateTypes = set of TGLStateType;
  43. const
  44. cAllAttribBits = [low(TGLStateType) .. High(TGLStateType)];
  45. type
  46. TGLMeshPrimitive = (
  47. mpNOPRIMITIVE,
  48. mpTRIANGLES,
  49. mpTRIANGLE_STRIP,
  50. mpTRIANGLE_FAN,
  51. mpPOINTS,
  52. mpLINES,
  53. mpLINE_LOOP,
  54. mpLINE_STRIP,
  55. mpLINES_ADJACENCY,
  56. mpLINE_STRIP_ADJACENCY,
  57. mpTRIANGLES_ADJACENCY,
  58. mpTRIANGLE_STRIP_ADJACENCY,
  59. mpPATCHES
  60. );
  61. TGLMeshPrimitives = set of TGLMeshPrimitive;
  62. const
  63. cAllMeshPrimitive = [
  64. mpTRIANGLES,
  65. mpTRIANGLE_STRIP,
  66. mpTRIANGLE_FAN,
  67. mpPOINTS,
  68. mpLINES,
  69. mpLINE_LOOP,
  70. mpLINE_STRIP,
  71. mpLINES_ADJACENCY,
  72. mpLINE_STRIP_ADJACENCY,
  73. mpTRIANGLES_ADJACENCY,
  74. mpTRIANGLE_STRIP_ADJACENCY,
  75. mpPATCHES];
  76. type
  77. // Reflects all relevant (binary) states of OpenGL subsystem
  78. TGLState = (stAlphaTest, stAutoNormal,
  79. stBlend, stColorMaterial, stCullFace, stDepthTest, stDither,
  80. stFog, stLighting, stLineSmooth, stLineStipple,
  81. stIndexLogicOp, stColorLogicOp, stNormalize, stPointSmooth, stPointSprite,
  82. stPolygonSmooth, stPolygonStipple, stScissorTest, stStencilTest,
  83. stPolygonOffsetPoint, stPolygonOffsetLine, stPolygonOffsetFill,
  84. stDepthClamp);
  85. TGLStates = set of TGLState;
  86. TGLComparisonFunction = (cfNever, cfAlways, cfLess, cfLEqual, cfEqual,
  87. cfGreater, cfNotEqual, cfGEqual);
  88. TGLStencilFunction = TGLComparisonFunction;
  89. TGLDepthFunction = TGLComparisonFunction;
  90. TGLBlendFunction = (bfZero, bfOne,
  91. bfSrcColor, bfOneMinusSrcColor, bfDstColor, bfOneMinusDstColor,
  92. bfSrcAlpha, bfOneMinusSrcAlpha, bfDstAlpha, bfOneMinusDstAlpha,
  93. bfConstantColor, bfOneMinusConstantColor,
  94. bfConstantAlpha, bfOneMinusConstantAlpha,
  95. bfSrcAlphaSat);
  96. TGLDstBlendFunction = bfZero..bfOneMinusConstantAlpha;
  97. TGLBlendEquation = (beAdd, beSubtract, beReverseSubtract, beMin, beMax);
  98. TGLStencilOp = (soKeep, soZero, soReplace, soIncr, soDecr, soInvert, soIncrWrap,
  99. soDecrWrap);
  100. TGLLogicOp = (loClear, loAnd, loAndReverse, loCopy, loAndInverted, loNoOp,
  101. loXOr, loOr, loNor, loEquiv, loInvert, loOrReverse, loCopyInverted,
  102. loOrInverted, loNAnd, loSet);
  103. TGLQueryType = (
  104. qrySamplesPassed,
  105. qryPrimitivesGenerated,
  106. qryTransformFeedbackPrimitivesWritten,
  107. qryTimeElapsed,
  108. qryAnySamplesPassed);
  109. // Describe what kind of winding has a front face
  110. TGLFaceWinding = (fwCounterClockWise, fwClockWise);
  111. TGLPolygonMode = (pmFill, pmLines, pmPoints);
  112. TGLCullFaceMode = (cmFront, cmBack, cmFrontAndBack);
  113. // TSingleCullFaceMode = cmFront..cmBack;
  114. TGLColorComponent = (ccRed, ccGreen, ccBlue, ccAlpha);
  115. TGLColorMask = set of TGLColorComponent;
  116. const
  117. cAllColorComponents = [ccRed, ccGreen, ccBlue, ccAlpha];
  118. MAX_HARDWARE_LIGHT = 16;
  119. MAX_SHADER_LIGHT = 8;
  120. MAX_HARDWARE_TEXTURE_UNIT = 48;
  121. MAX_HARDWARE_UNIFORM_BUFFER_BINDING = 75;
  122. type
  123. TGLHintType = (hintDontCare, hintFastest, hintNicest);
  124. TGLLightSourceState = packed record
  125. Position: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  126. Ambient: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  127. Diffuse: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  128. Specular: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  129. SpotDirection: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  130. SpotCosCutoffExponent: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  131. Attenuation: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLVector;
  132. end;
  133. TGLShaderLightSourceState = packed record
  134. Position: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  135. Ambient: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  136. Diffuse: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  137. Specular: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  138. SpotDirection: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  139. SpotCosCutoffExponent: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  140. Attenuation: array [0 .. MAX_SHADER_LIGHT - 1] of TGLVector;
  141. end;
  142. TGLOnLightsChanged = procedure(Sender: TObject);
  143. TGLBufferBindingTarget = (bbtUniform, bbtTransformFeedBack);
  144. TUBOStates = record
  145. FUniformBufferBinding: Cardinal;
  146. FOffset: TGLintptr;
  147. FSize: TGLsizeiptr;
  148. end;
  149. TGLMaterialLevel = (mlAuto, mlFixedFunction, mlMultitexturing, mlSM3, mlSM4, mlSM5);
  150. (* Manages an application-side cache of OpenGL states and parameters.
  151. Purpose of this class is to eliminate redundant state and parameter
  152. changes, and there will typically be no more than one state cache per
  153. OpenGL context *)
  154. TGLStateCache = class
  155. strict private
  156. // Legacy state
  157. FFrontBackColors: array [0 .. 1, 0 .. 3] of TGLVector;
  158. FFrontBackShininess: array [0 .. 1] of Integer;
  159. FAlphaFunc: TGLComparisonFunction;
  160. FAlphaRef: Single;
  161. FPolygonBackMode: TGLPolygonMode; // Front + back have same polygon mode
  162. // Lighting state
  163. FMaxLights: Cardinal;
  164. FLightEnabling: array [0 .. MAX_HARDWARE_LIGHT - 1] of Boolean;
  165. FLightIndices: array [0 .. MAX_HARDWARE_LIGHT - 1] of TGLint;
  166. FLightNumber: Integer;
  167. FLightStates: TGLLightSourceState;
  168. FSpotCutoff: array [0 .. MAX_HARDWARE_LIGHT - 1] of Single;
  169. FShaderLightStates: TGLShaderLightSourceState;
  170. FShaderLightStatesChanged: Boolean;
  171. FColorWriting: Boolean; // TODO: change to per draw buffer (FColorWriteMask)
  172. FStates: TGLStates;
  173. FListStates: array of TGLStateTypes;
  174. FCurrentList: Cardinal;
  175. FTextureMatrixIsIdentity: array [0 .. 3] of Boolean;
  176. // FForwardContext: Boolean;
  177. FFFPLight: Boolean;
  178. // Vertex Array Data state
  179. FVertexArrayBinding: Cardinal;
  180. FArrayBufferBinding: Cardinal;
  181. FElementBufferBinding: Cardinal;
  182. FTextureBufferBinding: Cardinal;
  183. FEnablePrimitiveRestart: TGLboolean;
  184. FPrimitiveRestartIndex: Cardinal;
  185. // Transformation state
  186. FViewPort: TVector4i;
  187. FDepthRange: array [0 .. 1] of TGLclampd;
  188. FEnableClipDistance: array [0 .. 7] of TGLboolean;
  189. FEnableDepthClamp: TGLboolean;
  190. // Coloring state
  191. FClampReadColor: Cardinal; // GL_FIXED_ONLY
  192. FProvokingVertex: Cardinal; // GL_LAST_VERTEX_CONVENTION
  193. // Rasterization state
  194. FPointSize: TGLfloat;
  195. FPointFadeThresholdSize: TGLfloat;
  196. FPointSpriteCoordOrigin: Cardinal; // GL_UPPER_LEFT
  197. FLineWidth: Single;
  198. FLineStippleFactor: TGLint;
  199. FLineStipplePattern: TGLushort;
  200. FEnableLineSmooth: TGLboolean;
  201. FEnableCullFace: TGLboolean;
  202. FCullFaceMode: TGLCullFaceMode;
  203. FFrontFace: TGLFaceWinding;
  204. FEnablePolygonSmooth: TGLboolean;
  205. FPolygonMode: TGLPolygonMode;
  206. FPolygonOffsetFactor: TGLfloat;
  207. FPolygonOffsetUnits: TGLfloat;
  208. FEnablePolygonOffsetPoint: TGLboolean;
  209. FEnablePolygonOffsetLine: TGLboolean;
  210. FEnablePolygonOffsetFill: TGLboolean;
  211. // Multisample state
  212. FEnableMultisample: TGLboolean;
  213. FEnableSampleAlphaToCoverage: TGLboolean;
  214. FEnableSampleAlphaToOne: TGLboolean;
  215. FEnableSampleCoverage: TGLboolean;
  216. FSampleCoverageValue: TGLfloat;
  217. FSampleCoverageInvert: TGLboolean;
  218. FEnableSampleMask: TGLboolean;
  219. FSampleMaskValue: array [0 .. 15] of TGLbitfield;
  220. // Texture state
  221. FMaxTextureSize: Cardinal;
  222. FMax3DTextureSize: Cardinal;
  223. FMaxCubeTextureSize: Cardinal;
  224. FMaxArrayTextureSize: Cardinal;
  225. FMaxTextureImageUnits: Cardinal;
  226. FMaxTextureAnisotropy: Cardinal;
  227. FMaxSamples: Cardinal;
  228. FTextureBinding: array [0 .. MAX_HARDWARE_TEXTURE_UNIT - 1, TGLTextureTarget] of Cardinal;
  229. FTextureBindingTime: array [0 .. MAX_HARDWARE_TEXTURE_UNIT - 1, TGLTextureTarget] of Double;
  230. FSamplerBinding: array [0 .. MAX_HARDWARE_TEXTURE_UNIT - 1] of Cardinal;
  231. // Active texture state
  232. FActiveTexture: TGLint; // 0 .. Max_texture_units
  233. FActiveTextureEnabling: array [0 .. MAX_HARDWARE_TEXTURE_UNIT - 1, TGLTextureTarget] of Boolean;
  234. // Pixel operation state
  235. FEnableScissorTest: TGLboolean;
  236. FScissorBox: TVector4i;
  237. FEnableStencilTest: TGLboolean;
  238. FStencilFunc: TGLStencilFunction;
  239. FStencilValueMask: Cardinal;
  240. FStencilRef: TGLint;
  241. FStencilFail: TGLStencilOp;
  242. FStencilPassDepthFail: TGLStencilOp;
  243. FStencilPassDepthPass: TGLStencilOp;
  244. FStencilBackFunc: TGLStencilFunction;
  245. FStencilBackValueMask: Cardinal;
  246. FStencilBackRef: Cardinal;
  247. FStencilBackFail: TGLStencilOp;
  248. FStencilBackPassDepthPass: TGLStencilOp;
  249. FStencilBackPassDepthFail: TGLStencilOp;
  250. FEnableDepthTest: TGLboolean;
  251. FDepthFunc: TGLDepthFunction;
  252. FEnableBlend: array [0 .. 15] of TGLboolean;
  253. FBlendSrcRGB: TGLBlendFunction;
  254. FBlendSrcAlpha: TGLBlendFunction;
  255. FBlendDstRGB: TGLDstBlendFunction;
  256. FBlendDstAlpha: TGLDstBlendFunction;
  257. FBlendEquationRGB: TGLBlendEquation;
  258. FBlendEquationAlpha: TGLBlendEquation;
  259. FBlendColor: TGLVector;
  260. FEnableFramebufferSRGB: TGLboolean;
  261. FEnableDither: TGLboolean;
  262. FEnableColorLogicOp: TGLboolean;
  263. FLogicOpMode: TGLLogicOp;
  264. // Framebuffer control state
  265. FColorWriteMask: array [0 .. 15] of TGLColorMask;
  266. FDepthWriteMask: TGLboolean;
  267. FStencilWriteMask: Cardinal;
  268. FStencilBackWriteMask: Cardinal;
  269. FColorClearValue: TGLVector;
  270. FDepthClearValue: TGLfloat;
  271. FStencilClearValue: Cardinal;
  272. // Framebuffer state
  273. FDrawFrameBuffer: Cardinal;
  274. FReadFrameBuffer: Cardinal;
  275. // Renderbuffer state
  276. FRenderBuffer: Cardinal;
  277. // Pixels state
  278. FUnpackSwapBytes: TGLboolean;
  279. FUnpackLSBFirst: TGLboolean;
  280. FUnpackImageHeight: Cardinal;
  281. FUnpackSkipImages: Cardinal;
  282. FUnpackRowLength: Cardinal;
  283. FUnpackSkipRows: Cardinal;
  284. FUnpackSkipPixels: Cardinal;
  285. FUnpackAlignment: Cardinal;
  286. FPackSwapBytes: TGLboolean;
  287. FPackLSBFirst: TGLboolean;
  288. FPackImageHeight: Cardinal;
  289. FPackSkipImages: Cardinal;
  290. FPackRowLength: Cardinal;
  291. FPackSkipRows: Cardinal;
  292. FPackSkipPixels: Cardinal;
  293. FPackAlignment: Cardinal;
  294. FPixelPackBufferBinding: Cardinal;
  295. FPixelUnpackBufferBinding: Cardinal;
  296. // Program state
  297. FCurrentProgram: Cardinal;
  298. FMaxTextureUnits: Cardinal;
  299. FUniformBufferBinding: Cardinal;
  300. FUBOStates: array [TGLBufferBindingTarget, 0 .. MAX_HARDWARE_UNIFORM_BUFFER_BINDING - 1] of TUBOStates;
  301. // Vector + Geometry Shader state
  302. FCurrentVertexAttrib: array [0 .. 15] of TGLVector;
  303. FEnableProgramPointSize: TGLboolean;
  304. // Transform Feedback state
  305. FTransformFeedbackBufferBinding: Cardinal;
  306. // Hints state
  307. FTextureCompressionHint: TGLHintType;
  308. FPolygonSmoothHint: TGLHintType;
  309. FFragmentShaderDerivitiveHint: TGLHintType;
  310. FLineSmoothHint: TGLHintType;
  311. FMultisampleFilterHint: TGLHintType;
  312. // Misc state
  313. FCurrentQuery: array [TGLQueryType] of Cardinal;
  314. FCopyReadBufferBinding: Cardinal;
  315. FCopyWriteBufferBinding: Cardinal;
  316. FEnableTextureCubeMapSeamless: TGLboolean;
  317. FInsideList: Boolean;
  318. FOnLightsChanged: TGLOnLightsChanged;
  319. protected
  320. // Vertex Array Data state
  321. procedure SetVertexArrayBinding(const Value: Cardinal); inline;
  322. function GetArrayBufferBinding: Cardinal; inline;
  323. procedure SetArrayBufferBinding(const Value: Cardinal); inline;
  324. function GetElementBufferBinding: Cardinal; inline;
  325. procedure SetElementBufferBinding(const Value: Cardinal); inline;
  326. function GetEnablePrimitiveRestart: TGLboolean; inline;
  327. function GetPrimitiveRestartIndex: Cardinal; inline;
  328. procedure SetEnablePrimitiveRestart(const enabled: TGLboolean); inline;
  329. procedure SetPrimitiveRestartIndex(const index: Cardinal); inline;
  330. procedure SetTextureBufferBinding(const Value: Cardinal); inline;
  331. // Transformation state
  332. procedure SetViewPort(const Value: TVector4i); inline;
  333. function GetEnableClipDistance(ClipDistance: Cardinal): TGLboolean; inline;
  334. procedure SetEnableClipDistance(index: Cardinal; const Value: TGLboolean); inline;
  335. function GetDepthRangeFar: TGLclampd; inline;
  336. procedure SetDepthRangeFar(const Value: TGLclampd); inline;
  337. function GetDepthRangeNear: TGLclampd; inline;
  338. procedure SetDepthRangeNear(const Value: TGLclampd); inline;
  339. procedure SetEnableDepthClamp(const enabled: TGLboolean); inline;
  340. // Coloring state
  341. procedure SetClampReadColor(const Value: Cardinal); inline;
  342. procedure SetProvokingVertex(const Value: Cardinal); inline;
  343. // Rasterization state
  344. procedure SetPointSize(const Value: TGLfloat); inline;
  345. procedure SetPointFadeThresholdSize(const Value: TGLfloat); inline;
  346. procedure SetPointSpriteCoordOrigin(const Value: Cardinal); inline;
  347. procedure SetLineWidth(const Value: TGLfloat); inline;
  348. procedure SetLineStippleFactor(const Value: TGLint); inline;
  349. procedure SetLineStipplePattern(const Value: TGLushort); inline;
  350. procedure SetEnableLineSmooth(const Value: TGLboolean); inline;
  351. procedure SetEnableCullFace(const Value: TGLboolean); inline;
  352. procedure SetCullFaceMode(const Value: TGLCullFaceMode); inline;
  353. procedure SetFrontFace(const Value: TGLFaceWinding); inline;
  354. procedure SetEnablePolygonSmooth(const Value: TGLboolean); inline;
  355. procedure SetPolygonMode(const Value: TGLPolygonMode); inline;
  356. procedure SetPolygonOffsetFactor(const Value: TGLfloat); inline;
  357. procedure SetPolygonOffsetUnits(const Value: TGLfloat); inline;
  358. procedure SetEnablePolygonOffsetPoint(const Value: TGLboolean); inline;
  359. procedure SetEnablePolygonOffsetLine(const Value: TGLboolean); inline;
  360. procedure SetEnablePolygonOffsetFill(const Value: TGLboolean); inline;
  361. // Multisample state
  362. procedure SetEnableMultisample(const Value: TGLboolean); inline;
  363. procedure SetEnableSampleAlphaToCoverage(const Value: TGLboolean); inline;
  364. procedure SetEnableSampleAlphaToOne(const Value: TGLboolean); inline;
  365. procedure SetEnableSampleCoverage(const Value: TGLboolean); inline;
  366. procedure SetSampleCoverageValue(const Value: TGLfloat); inline;
  367. procedure SetSampleCoverageInvert(const Value: TGLboolean); inline;
  368. procedure SetEnableSampleMask(const Value: TGLboolean); inline;
  369. function GetSampleMaskValue(index: Integer): TGLbitfield; inline;
  370. procedure SetSampleMaskValue(index: Integer; const Value: TGLbitfield); inline;
  371. // Texture state
  372. function GetMaxTextureSize: Cardinal; inline;
  373. function GetMax3DTextureSize: Cardinal; inline;
  374. function GetMaxCubeTextureSize: Cardinal; inline;
  375. function GetMaxArrayTextureSize: Cardinal; inline;
  376. function GetMaxTextureImageUnits: Cardinal; inline;
  377. function GetMaxTextureAnisotropy: Cardinal; inline;
  378. function GetMaxSamples: Cardinal; inline;
  379. function GetTextureBinding(index: Integer; target: TGLTextureTarget): Cardinal; inline;
  380. function GetTextureBindingTime(index: Integer; target: TGLTextureTarget): Double; inline;
  381. procedure SetTextureBinding(index: Integer; target: TGLTextureTarget; const Value: Cardinal);
  382. function GetActiveTextureEnabled(target: TGLTextureTarget): Boolean; inline;
  383. procedure SetActiveTextureEnabled(target: TGLTextureTarget; const Value: Boolean); inline;
  384. function GetSamplerBinding(index: Cardinal): Cardinal; inline;
  385. procedure SetSamplerBinding(index: Cardinal; const Value: Cardinal); inline;
  386. // Active texture
  387. procedure SetActiveTexture(const Value: TGLint); inline;
  388. // Pixel operations
  389. procedure SetEnableScissorTest(const Value: TGLboolean); inline;
  390. procedure SetScissorBox(const Value: TVector4i); inline;
  391. procedure SetEnableStencilTest(const Value: TGLboolean); inline;
  392. procedure SetEnableDepthTest(const Value: TGLboolean); inline;
  393. procedure SetDepthFunc(const Value: TGLDepthFunction); inline;
  394. function GetEnableBlend(index: Integer): TGLboolean; inline;
  395. procedure SetEnableBlend(index: Integer; const Value: TGLboolean); inline;
  396. procedure SetBlendColor(const Value: TGLVector); inline;
  397. procedure SetEnableFramebufferSRGB(const Value: TGLboolean); inline;
  398. procedure SetEnableDither(const Value: TGLboolean); inline;
  399. procedure SetEnableColorLogicOp(const Value: TGLboolean); inline;
  400. procedure SetLogicOpMode(const Value: TGLLogicOp); inline;
  401. // Framebuffer control
  402. function GetColorWriteMask(index: Integer): TGLColorMask; inline;
  403. procedure SetColorWriteMask(index: Integer; const Value: TGLColorMask); inline;
  404. procedure SetDepthWriteMask(const Value: TGLboolean); inline;
  405. procedure SetStencilWriteMask(const Value: Cardinal); inline;
  406. procedure SetStencilBackWriteMask(const Value: Cardinal); inline;
  407. procedure SetColorClearValue(const Value: TGLVector); inline;
  408. procedure SetDepthClearValue(const Value: TGLfloat); inline;
  409. procedure SetStencilClearValue(const Value: Cardinal); inline;
  410. // Framebuffer
  411. procedure SetDrawFrameBuffer(const Value: Cardinal); inline;
  412. procedure SetReadFrameBuffer(const Value: Cardinal); inline;
  413. // Renderbuffer
  414. procedure SetRenderBuffer(const Value: Cardinal); inline;
  415. // Pixels
  416. procedure SetUnpackSwapBytes(const Value: TGLboolean); inline;
  417. procedure SetUnpackLSBFirst(const Value: TGLboolean); inline;
  418. procedure SetUnpackImageHeight(const Value: Cardinal); inline;
  419. procedure SetUnpackSkipImages(const Value: Cardinal); inline;
  420. procedure SetUnpackRowLength(const Value: Cardinal); inline;
  421. procedure SetUnpackSkipRows(const Value: Cardinal); inline;
  422. procedure SetUnpackSkipPixels(const Value: Cardinal); inline;
  423. procedure SetUnpackAlignment(const Value: Cardinal); inline;
  424. procedure SetPackSwapBytes(const Value: TGLboolean); inline;
  425. procedure SetPackLSBFirst(const Value: TGLboolean); inline;
  426. procedure SetPackImageHeight(const Value: Cardinal); inline;
  427. procedure SetPackSkipImages(const Value: Cardinal); inline;
  428. procedure SetPackRowLength(const Value: Cardinal); inline;
  429. procedure SetPackSkipRows(const Value: Cardinal); inline;
  430. procedure SetPackSkipPixels(const Value: Cardinal); inline;
  431. procedure SetPackAlignment(const Value: Cardinal); inline;
  432. procedure SetPixelPackBufferBinding(const Value: Cardinal);
  433. procedure SetPixelUnpackBufferBinding(const Value: Cardinal);
  434. // Program
  435. procedure SetCurrentProgram(const Value: Cardinal); inline;
  436. procedure SetUniformBufferBinding(const Value: Cardinal); inline;
  437. function GetMaxTextureUnits: Cardinal; inline;
  438. // Vector + Geometry Shader state
  439. function GetCurrentVertexAttrib(index: Integer): TGLVector; inline;
  440. procedure SetCurrentVertexAttrib(index: Integer; const Value: TGLVector); inline;
  441. procedure SetEnableProgramPointSize(const Value: TGLboolean); inline;
  442. // Transform Feedback state
  443. procedure SetTransformFeedbackBufferBinding(const Value: Cardinal); inline;
  444. // Hints
  445. procedure SetLineSmoothHint(const Value: TGLHintType); inline;
  446. procedure SetPolygonSmoothHint(const Value: TGLHintType); inline;
  447. procedure SetTextureCompressionHint(const Value: TGLHintType); inline;
  448. procedure SetFragmentShaderDerivitiveHint(const Value: TGLHintType); inline;
  449. procedure SetMultisampleFilterHint(const Value: TGLHintType); inline;
  450. // Misc
  451. function GetCurrentQuery(index: TGLQueryType): Cardinal; inline;
  452. // procedure SetCurrentQuery(Index: TQueryType; const Value: Cardinal);
  453. procedure SetCopyReadBufferBinding(const Value: Cardinal); inline;
  454. procedure SetCopyWriteBufferBinding(const Value: Cardinal); inline;
  455. procedure SetEnableTextureCubeMapSeamless(const Value: TGLboolean); inline;
  456. // Ligting
  457. procedure SetFFPLight(Value: Boolean); inline;
  458. function GetMaxLights: Integer; inline;
  459. function GetLightEnabling(I: Integer): Boolean; inline;
  460. procedure SetLightEnabling(I: Integer; Value: Boolean); inline;
  461. function GetLightPosition(I: Integer): TGLVector; inline;
  462. procedure SetLightPosition(I: Integer; const Value: TGLVector); inline;
  463. function GetLightSpotDirection(I: Integer): TAffineVector; inline;
  464. procedure SetLightSpotDirection(I: Integer; const Value: TAffineVector); inline;
  465. function GetLightAmbient(I: Integer): TGLVector; inline;
  466. procedure SetLightAmbient(I: Integer; const Value: TGLVector); inline;
  467. function GetLightDiffuse(I: Integer): TGLVector; inline;
  468. procedure SetLightDiffuse(I: Integer; const Value: TGLVector); inline;
  469. function GetLightSpecular(I: Integer): TGLVector; inline;
  470. procedure SetLightSpecular(I: Integer; const Value: TGLVector); inline;
  471. function GetSpotCutoff(I: Integer): Single; inline;
  472. procedure SetSpotCutoff(I: Integer; const Value: Single); inline;
  473. function GetSpotExponent(I: Integer): Single; inline;
  474. procedure SetSpotExponent(I: Integer; const Value: Single); inline;
  475. function GetConstantAtten(I: Integer): Single; inline;
  476. procedure SetConstantAtten(I: Integer; const Value: Single); inline;
  477. function GetLinearAtten(I: Integer): Single; inline;
  478. procedure SetLinearAtten(I: Integer; const Value: Single); inline;
  479. function GetQuadAtten(I: Integer): Single; inline;
  480. procedure SetQuadAtten(I: Integer; const Value: Single); inline;
  481. procedure SetForwardContext(Value: Boolean); inline;
  482. function GetMaterialAmbient(const aFace: TGLCullFaceMode): TGLVector; inline;
  483. function GetMaterialDiffuse(const aFace: TGLCullFaceMode): TGLVector; inline;
  484. function GetMaterialSpecular(const aFace: TGLCullFaceMode): TGLVector; inline;
  485. function GetMaterialEmission(const aFace: TGLCullFaceMode): TGLVector; inline;
  486. function GetMaterialShininess(const aFace: TGLCullFaceMode): Integer; inline;
  487. public
  488. constructor Create; virtual;
  489. destructor Destroy; override;
  490. procedure PushAttrib(const stateTypes: TGLStateTypes); inline;
  491. procedure PopAttrib(); inline;
  492. procedure Enable(const aState: TGLState);
  493. procedure Disable(const aState: TGLState);
  494. procedure PerformEnable(const aState: TGLState); inline;
  495. procedure PerformDisable(const aState: TGLState); inline;
  496. procedure SetGLState(const aState: TGLState); deprecated; inline;
  497. procedure UnSetGLState(const aState: TGLState); deprecated; inline;
  498. procedure ResetGLPolygonMode; deprecated; inline;
  499. procedure ResetGLMaterialColors; deprecated; inline;
  500. procedure ResetGLTexture(const TextureUnit: Integer); deprecated; inline;
  501. procedure ResetGLCurrentTexture; deprecated;
  502. procedure ResetGLFrontFace; deprecated;
  503. procedure SetGLFrontFaceCW; deprecated; inline;
  504. procedure ResetAll; deprecated; inline;
  505. // Adjusts material colors for a face
  506. procedure SetGLMaterialColors(const aFace: TGLCullFaceMode; const emission, Ambient, Diffuse, Specular: TGLVector;
  507. const shininess: Integer);
  508. property MaterialAmbient[const aFace: TGLCullFaceMode]: TGLVector read GetMaterialAmbient;
  509. property MaterialDiffuse[const aFace: TGLCullFaceMode]: TGLVector read GetMaterialDiffuse;
  510. property MaterialSpecular[const aFace: TGLCullFaceMode]: TGLVector read GetMaterialSpecular;
  511. property MaterialEmission[const aFace: TGLCullFaceMode]: TGLVector read GetMaterialEmission;
  512. property MaterialShininess[const aFace: TGLCullFaceMode]: Integer read GetMaterialShininess;
  513. // Adjusts material alpha channel for a face
  514. procedure SetGLMaterialAlphaChannel(const aFace: Cardinal; const alpha: TGLfloat);
  515. // Adjusts material diffuse color for a face
  516. procedure SetGLMaterialDiffuseColor(const aFace: Cardinal; const Diffuse: TGLVector);
  517. // Lighting states
  518. property FixedFunctionPipeLight: Boolean read FFFPLight write SetFFPLight;
  519. property MaxLights: Integer read GetMaxLights;
  520. property LightEnabling[Index: Integer]: Boolean read GetLightEnabling write SetLightEnabling;
  521. property LightPosition[Index: Integer]: TGLVector read GetLightPosition write SetLightPosition;
  522. property LightSpotDirection[Index: Integer]: TAffineVector read GetLightSpotDirection write SetLightSpotDirection;
  523. property LightAmbient[Index: Integer]: TGLVector read GetLightAmbient write SetLightAmbient;
  524. property LightDiffuse[Index: Integer]: TGLVector read GetLightDiffuse write SetLightDiffuse;
  525. property LightSpecular[Index: Integer]: TGLVector read GetLightSpecular write SetLightSpecular;
  526. property LightSpotCutoff[Index: Integer]: Single read GetSpotCutoff write SetSpotCutoff;
  527. property LightSpotExponent[Index: Integer]: Single read GetSpotExponent write SetSpotExponent;
  528. property LightConstantAtten[Index: Integer]: Single read GetConstantAtten write SetConstantAtten;
  529. property LightLinearAtten[Index: Integer]: Single read GetLinearAtten write SetLinearAtten;
  530. property LightQuadraticAtten[Index: Integer]: Single read GetQuadAtten write SetQuadAtten;
  531. function GetLightIndicesAsAddress: PGLInt;
  532. function GetLightStateAsAddress: Pointer;
  533. property LightNumber: Integer read FLightNumber;
  534. property OnLightsChanged: TGLOnLightsChanged read FOnLightsChanged write FOnLightsChanged;
  535. // Blending states
  536. procedure SetGLAlphaFunction(func: TGLComparisonFunction; ref: Single); inline;
  537. // Vertex Array Data state
  538. (* The currently bound array buffer (calling glVertexAttribPointer
  539. locks this buffer to the currently bound VBO). *)
  540. property VertexArrayBinding: Cardinal read FVertexArrayBinding write SetVertexArrayBinding;
  541. // The currently bound vertex buffer object (VAO)
  542. property ArrayBufferBinding: Cardinal read GetArrayBufferBinding write SetArrayBufferBinding;
  543. // The currently bound element buffer object (EBO)
  544. property ElementBufferBinding: Cardinal read GetElementBufferBinding write SetElementBufferBinding;
  545. // Determines whether primitive restart is turned on or off
  546. property EnablePrimitiveRestart: TGLboolean read GetEnablePrimitiveRestart write SetEnablePrimitiveRestart;
  547. // The index Value that causes a primitive restart
  548. property PrimitiveRestartIndex: Cardinal read GetPrimitiveRestartIndex write SetPrimitiveRestartIndex;
  549. // The currently bound texture buffer object (TBO)
  550. property TextureBufferBinding: Cardinal read FTextureBufferBinding write SetTextureBufferBinding;
  551. // Transformation state
  552. property ViewPort: TVector4i read FViewPort write SetViewPort;
  553. // Modifies the near + far clipping planes
  554. procedure SetDepthRange(const ZNear, ZFar: TGLclampd); inline;
  555. // The near clipping plane distance
  556. property DepthRangeNear: TGLclampd read GetDepthRangeNear write SetDepthRangeNear;
  557. // The far clipping plane distance
  558. property DepthRangeFar: TGLclampd read GetDepthRangeFar write SetDepthRangeFar;
  559. // Enables/Disables each of the clip distances, used in shaders
  560. property EnableClipDistance[Index: Cardinal]: TGLboolean read GetEnableClipDistance write SetEnableClipDistance;
  561. // Enables/Disables depth clamping
  562. property EnableDepthClamp: TGLboolean read FEnableDepthClamp write SetEnableDepthClamp;
  563. // Coloring state Controls read color clamping
  564. property ClampReadColor: Cardinal read FClampReadColor write SetClampReadColor;
  565. (* The provoking vertex used in flat shading. All the vertices of each
  566. primitive will the same value determined by this property. *)
  567. property ProvokingVertex: Cardinal read FProvokingVertex write SetProvokingVertex;
  568. // Rasterization state
  569. (* The default point size, used when EnableProgramPointSize = false *)
  570. property PointSize: TGLfloat read FPointSize write SetPointSize;
  571. // If multisampling is enabled, this can control when points are faded out
  572. property PointFadeThresholdSize: TGLfloat read FPointFadeThresholdSize write SetPointFadeThresholdSize;
  573. // The texture coordinate origin of point sprites
  574. property PointSpriteCoordOrigin: Cardinal read FPointSpriteCoordOrigin write SetPointSpriteCoordOrigin;
  575. // The line width
  576. property LineWidth: TGLfloat read FLineWidth write SetLineWidth;
  577. // The line stipple
  578. property LineStippleFactor: TGLint read FLineStippleFactor write SetLineStippleFactor;
  579. // The line stipple
  580. property LineStipplePattern: TGLushort read FLineStipplePattern write SetLineStipplePattern;
  581. // Enable/Disable line smoothing
  582. property EnableLineSmooth: TGLboolean read FEnableLineSmooth write SetEnableLineSmooth;
  583. // Enable/Disable face culling
  584. property EnableCullFace: TGLboolean read FEnableCullFace write SetEnableCullFace;
  585. // Selects which faces to cull: front, back or front+back
  586. property CullFaceMode: TGLCullFaceMode read FCullFaceMode write SetCullFaceMode;
  587. // The winding direction that indicates a front facing primitive
  588. property FrontFace: { Cardinal } TGLFaceWinding read FFrontFace write SetFrontFace;
  589. // Enables/Disables polygon smoothing.
  590. property EnablePolygonSmooth: TGLboolean read FEnablePolygonSmooth write SetEnablePolygonSmooth;
  591. // Whether polygons appear filled, lines or points
  592. property PolygonMode: TGLPolygonMode read FPolygonMode write SetPolygonMode;
  593. // Scales the maximum depth of the polygon
  594. property PolygonOffsetFactor: TGLfloat read FPolygonOffsetFactor write SetPolygonOffsetFactor;
  595. // Scales an implementation-dependent constant that relates to the usable resolution of the depth buffer
  596. property PolygonOffsetUnits: TGLfloat read FPolygonOffsetUnits write SetPolygonOffsetUnits;
  597. // Set polygon offset
  598. procedure SetPolygonOffset(const factor, units: TGLfloat);
  599. // Enable/Disable polygon offset for polygons in point mode
  600. property EnablePolygonOffsetPoint: TGLboolean read FEnablePolygonOffsetPoint write SetEnablePolygonOffsetPoint;
  601. // Enable/Disable polygon offset for polygons in line mode
  602. property EnablePolygonOffsetLine: TGLboolean read FEnablePolygonOffsetLine write SetEnablePolygonOffsetLine;
  603. // Enable/Disable polygon offset for polygons in fill mode
  604. property EnablePolygonOffsetFill: TGLboolean read FEnablePolygonOffsetFill write SetEnablePolygonOffsetFill;
  605. // Multisample state
  606. // Enable/Disable multisampling
  607. property EnableMultisample: TGLboolean read FEnableMultisample write SetEnableMultisample;
  608. // Enable/Disable sample alpha to coverage
  609. property EnableSampleAlphaToCoverage: TGLboolean read FEnableSampleAlphaToCoverage write SetEnableSampleAlphaToCoverage;
  610. // Enable/Disable sample alpha to one
  611. property EnableSampleAlphaToOne: TGLboolean read FEnableSampleAlphaToOne write SetEnableSampleAlphaToOne;
  612. // Enable/Disable sample coverage
  613. property EnableSampleCoverage: TGLboolean read FEnableSampleCoverage write SetEnableSampleCoverage;
  614. // Sample coverage Value
  615. property SampleCoverageValue: TGLfloat read FSampleCoverageValue write SetSampleCoverageValue;
  616. // Inverts sample coverage Value
  617. property SampleCoverageInvert: TGLboolean read FSampleCoverageInvert write SetSampleCoverageInvert;
  618. // Set sample coverage
  619. procedure SetSampleCoverage(const Value: TGLfloat; invert: TGLboolean);
  620. // Enable/Disable sample mask
  621. property EnableSampleMask: TGLboolean read FEnableSampleMask write SetEnableSampleMask;
  622. // Sample mask values
  623. property SampleMaskValue[Index: Integer]: TGLbitfield read GetSampleMaskValue write SetSampleMaskValue;
  624. // Textures
  625. // Textures bound to each texture unit + binding point.
  626. property TextureBinding[Index: Integer; target: TGLTextureTarget]: Cardinal read GetTextureBinding write SetTextureBinding;
  627. property TextureBindingTime[Index: Integer; target: TGLTextureTarget]: Double read GetTextureBindingTime;
  628. property ActiveTextureEnabled[target: TGLTextureTarget]: Boolean read GetActiveTextureEnabled write SetActiveTextureEnabled;
  629. property SamplerBinding[Index: Cardinal]: Cardinal read GetSamplerBinding write SetSamplerBinding;
  630. property MaxTextureSize: Cardinal read GetMaxTextureSize;
  631. property Max3DTextureSize: Cardinal read GetMax3DTextureSize;
  632. property MaxCubeTextureSize: Cardinal read GetMaxCubeTextureSize;
  633. property MaxArrayTextureSize: Cardinal read GetMaxArrayTextureSize;
  634. property MaxTextureImageUnits: Cardinal read GetMaxTextureImageUnits;
  635. property MaxTextureAnisotropy: Cardinal read GetMaxTextureAnisotropy;
  636. property MaxSamples: Cardinal read GetMaxSamples;
  637. // TODO: GL_TEXTURE_BUFFER_DATA_STORE_BINDING ?
  638. // Active texture
  639. (* The active texture unit. Valid values are 0 .. Max texture units. *)
  640. property ActiveTexture: TGLint read FActiveTexture write SetActiveTexture;
  641. // Pixel operations
  642. (* Enables/Disables scissor test. *)
  643. property EnableScissorTest: TGLboolean read FEnableScissorTest write SetEnableScissorTest;
  644. // The bounding box used in scissor test.
  645. property ScissorBox: TVector4i read FScissorBox write SetScissorBox;
  646. // Enables/Disables stencil test.
  647. property EnableStencilTest: TGLboolean read FEnableStencilTest write SetEnableStencilTest;
  648. (* The stencil function. Determines the comparison function to be used
  649. when comparing the reference + stored stencil values. *)
  650. property StencilFunc: TGLStencilFunction read FStencilFunc;
  651. // write SetStencilFunc;
  652. (* The stencil value mask. Masks both the reference + stored stencil values *)
  653. property StencilValueMask: Cardinal read FStencilValueMask;
  654. // write SetStencilValueMask;
  655. (* The stencil reference value. Clamped to 0..255 with an 8 bit stencil. *)
  656. property StencilRef: TGLint read FStencilRef; // write SetStencilRef;
  657. // The operation to perform when stencil test fails.
  658. property StencilFail: TGLStencilOp read FStencilFail; // write SetStencilFail;
  659. // The operation to perform when stencil test passes + depth test fails.
  660. property StencilPassDepthFail: TGLStencilOp read FStencilPassDepthFail;
  661. // write SetStencilPassDepthFail;
  662. (* The operation to perform when stencil test passes + depth test passes. *)
  663. property StencilPassDepthPass: TGLStencilOp read FStencilPassDepthPass;
  664. // write SetStencilPassDepthPass;
  665. (* The stencil back function. Determines the comparison function to be
  666. used when comparing the reference + stored stencil values on back facing primitives. *)
  667. property StencilBackFunc: TGLStencilFunction read FStencilBackFunc;
  668. // write SetStencilBackFunc;
  669. (* The stencil back value mask. Masks both the reference + stored stencil values. *)
  670. property StencilBackValueMask: Cardinal read FStencilBackValueMask;
  671. // write SetStencilBackValueMask;
  672. (* The stencil back reference value. Clamped to 0..255 with an 8 bit stencil. *)
  673. property StencilBackRef: Cardinal read FStencilBackRef;
  674. // write SetStencilBackRef;
  675. (* The operation to perform when stencil test fails on back facing primitives. *)
  676. property StencilBackFail: TGLStencilOp read FStencilBackFail;
  677. // write SetStencilBackFail;
  678. (* The operation to perform when stencil test passes + depth test fails on
  679. back facing primitives. *)
  680. property StencilBackPassDepthFail: TGLStencilOp read FStencilBackPassDepthFail;
  681. // write SetStencilBackPassDepthFail;
  682. (* The operation to perform when stencil test passes + depth test passes on
  683. back facing primitives. *)
  684. property StencilBackPassDepthPass: TGLStencilOp read FStencilBackPassDepthPass;
  685. // write SetStencilBackPassDepthPass;
  686. (* Used to set stencil Function, Reference + Mask values, for both front +
  687. back facing primitives. *)
  688. procedure SetStencilFunc(const func: TGLStencilFunction; const ref: TGLint; const mask: Cardinal); inline;
  689. (* Used to set stencil Function, Reference + Mask values for either the
  690. front or back facing primitives (or both, which is the same as calling
  691. SetStencilFunc). *)
  692. procedure SetStencilFuncSeparate(const face: TGLCullFaceMode; const func: TGLStencilFunction; const ref: TGLint;
  693. const mask: Cardinal); inline;
  694. // Used to set the StencilFail, StencilPassDepthFail + StencilPassDepthPass in one go.
  695. procedure SetStencilOp(const fail, zfail, zpass: TGLStencilOp); inline;
  696. (* Used to set the StencilFail, StencilPassDepthFail + StencilPassDepthPass
  697. in one go, for either front or back facing primitives. *)
  698. procedure SetStencilOpSeparate(const face: TGLCullFaceMode; const sfail, dpfail, dppass: TGLStencilOp); inline;
  699. // Enables/disables depth testing.
  700. property EnableDepthTest: TGLboolean read FEnableDepthTest write SetEnableDepthTest;
  701. (* The depth function. Used to determine whether to keep a fragment or
  702. discard it, depending on the current value stored in the depth buffer. *)
  703. property DepthFunc: TGLDepthFunction read FDepthFunc write SetDepthFunc;
  704. // Enables/disables blending for each draw buffer.
  705. property EnableBlend[Index: Integer]: TGLboolean read GetEnableBlend write SetEnableBlend;
  706. // The weighting factor used in blending equation, for source RGB.
  707. property BlendSrcRGB: TGLBlendFunction read FBlendSrcRGB;
  708. // write SetBlendSrcRGB;
  709. (* The weighting factor used in blending equation, for source alpha. *)
  710. property BlendSrcAlpha: TGLBlendFunction read FBlendSrcAlpha;
  711. // write SetBlendSrcAlpha;
  712. (* The weighting factor used in blending equation, for destination RGB. *)
  713. property BlendDstRGB: TGLDstBlendFunction read FBlendDstRGB;
  714. // write SetBlendDstRGB;
  715. (* The weighting factor used in blending equation, for destination alpha. *)
  716. property BlendDstAlpha: TGLDstBlendFunction read FBlendDstAlpha;
  717. // write SetBlendDstAlpha;
  718. (* Sets the weighting factors to be used by the blending equation, for both color + alpha *)
  719. procedure SetBlendFunc(const Src: TGLBlendFunction; const Dst: TGLDstBlendFunction); inline;
  720. (* Sets the weighting factors to be used by the blending equation, with
  721. separate values used for color + alpha components. *)
  722. procedure SetBlendFuncSeparate(const SrcRGB: TGLBlendFunction; const DstRGB: TGLDstBlendFunction;
  723. const SrcAlpha: TGLBlendFunction; const DstAlpha: TGLDstBlendFunction); inline;
  724. (* The blending equation. Determines how the incoming source fragment's
  725. RGB are combined with the destination RGB. *)
  726. property BlendEquationRGB: TGLBlendEquation read FBlendEquationRGB;
  727. // write SetBlendEquationRGB;
  728. (* The blending equation. Determines how the incoming source fragment's
  729. alpha values are combined with the destination alpha values. *)
  730. property BlendEquationAlpha: TGLBlendEquation read FBlendEquationAlpha;
  731. // write SetBlendEquationAlpha;
  732. // Sets the blend equation for RGB + alpha to the same value.
  733. procedure SetBlendEquation(const mode: TGLBlendEquation); inline;
  734. // Sets the blend equations for RGB + alpha separately.
  735. procedure SetBlendEquationSeparate(const modeRGB, modeAlpha: TGLBlendEquation); inline;
  736. // A constant blend color, that can be used in the blend equation.
  737. property BlendColor: TGLVector read FBlendColor write SetBlendColor;
  738. // Enables/disables framebuffer SRGB.
  739. property EnableFramebufferSRGB: TGLboolean read FEnableFramebufferSRGB write SetEnableFramebufferSRGB;
  740. // Enables/disables dithering.
  741. property EnableDither: TGLboolean read FEnableDither write SetEnableDither;
  742. // Enables/disables color logic op.
  743. property EnableColorLogicOp: TGLboolean read FEnableColorLogicOp write SetEnableColorLogicOp;
  744. // Logic op mode.
  745. property LogicOpMode: TGLLogicOp read FLogicOpMode write SetLogicOpMode;
  746. // The color write mask, for each draw buffer.
  747. property ColorWriteMask[Index: Integer]: TGLColorMask read GetColorWriteMask write SetColorWriteMask;
  748. // Set the color write mask for all draw buffers.
  749. procedure SetColorMask(mask: TGLColorMask); inline;
  750. // The depth write mask.
  751. property DepthWriteMask: TGLboolean read FDepthWriteMask write SetDepthWriteMask;
  752. // The stencil write mask.
  753. property StencilWriteMask: Cardinal read FStencilWriteMask write SetStencilWriteMask;
  754. // The stencil back write mask.
  755. property StencilBackWriteMask: Cardinal read FStencilBackWriteMask write SetStencilBackWriteMask;
  756. // The color clear value.
  757. property ColorClearValue: TGLVector read FColorClearValue write SetColorClearValue;
  758. // The depth clear value.
  759. property DepthClearValue: TGLfloat read FDepthClearValue write SetDepthClearValue;
  760. // The stencil clear value.
  761. property StencilClearValue: Cardinal read FStencilClearValue write SetStencilClearValue;
  762. // Framebuffer to be used for draw operations, 0 = default framebuffer.
  763. property DrawFrameBuffer: Cardinal read FDrawFrameBuffer write SetDrawFrameBuffer;
  764. // Framebuffer to be used for read operations, 0 = default framebuffer.
  765. property ReadFrameBuffer: Cardinal read FReadFrameBuffer write SetReadFrameBuffer;
  766. // set both draw + read framebuffer.
  767. procedure SetFrameBuffer(const Value: Cardinal); inline;
  768. // property FrameBuffer: Cardinal read FDrawFrameBuffer write SetFrameBuffer;
  769. // Renderbuffer currently bound render buffer.
  770. property RenderBuffer: Cardinal read FRenderBuffer write SetRenderBuffer;
  771. // Pixels
  772. (* Controls whether byte swapping occurs during pixel unpacking. *)
  773. property UnpackSwapBytes: TGLboolean read FUnpackSwapBytes write SetUnpackSwapBytes;
  774. // Whether unpacked data is required with LSB (least significant bit) first.
  775. property UnpackLSBFirst: TGLboolean read FUnpackLSBFirst write SetUnpackLSBFirst;
  776. // Unpack image height
  777. property UnpackImageHeight: Cardinal read FUnpackImageHeight write SetUnpackImageHeight;
  778. // Unpack skip images
  779. property UnpackSkipImages: Cardinal read FUnpackSkipImages write SetUnpackSkipImages;
  780. // Unpack row length
  781. property UnpackRowLength: Cardinal read FUnpackRowLength write SetUnpackRowLength;
  782. // Unpack skip rows
  783. property UnpackSkipRows: Cardinal read FUnpackSkipRows write SetUnpackSkipRows;
  784. // Unpack skip pixels
  785. property UnpackSkipPixels: Cardinal read FUnpackSkipPixels write SetUnpackSkipPixels;
  786. // Unpack alignment
  787. property UnpackAlignment: Cardinal read FUnpackAlignment write SetUnpackAlignment;
  788. // Controls whether byte swapping occurs during pixel packing
  789. property PackSwapBytes: TGLboolean read FPackSwapBytes write SetPackSwapBytes;
  790. // Whether packed data is required with LSB (least significant bit) first
  791. property PackLSBFirst: TGLboolean read FPackLSBFirst write SetPackLSBFirst;
  792. // Pack image height
  793. property PackImageHeight: Cardinal read FPackImageHeight write SetPackImageHeight;
  794. // Pack skip images
  795. property PackSkipImages: Cardinal read FPackSkipImages write SetPackSkipImages;
  796. // Pack row length
  797. property PackRowLength: Cardinal read FPackRowLength write SetPackRowLength;
  798. // Pack skip rows
  799. property PackSkipRows: Cardinal read FPackSkipRows write SetPackSkipRows;
  800. // Pack skip pixels
  801. property PackSkipPixels: Cardinal read FPackSkipPixels write SetPackSkipPixels;
  802. // Pack alignment
  803. property PackAlignment: Cardinal read FPackAlignment write SetPackAlignment;
  804. // Buffer bound for pixel packing (eg. ReadPixels)
  805. property PixelPackBufferBinding: Cardinal read FPixelPackBufferBinding write SetPixelPackBufferBinding;
  806. // Buffer bound for pixel unpacking (eg. Tex*Image)
  807. property PixelUnpackBufferBinding: Cardinal read FPixelUnpackBufferBinding write SetPixelUnpackBufferBinding;
  808. // Currently bound program
  809. property CurrentProgram: Cardinal read FCurrentProgram write SetCurrentProgram;
  810. property MaxTextureUnits: Cardinal read GetMaxTextureUnits;
  811. // Currently bound uniform buffer
  812. property UniformBufferBinding: Cardinal read FUniformBufferBinding write SetUniformBufferBinding;
  813. procedure SetBufferIndexedBinding(const Value: Cardinal; ATarget: TGLBufferBindingTarget; AIndex: Cardinal;
  814. ABufferSize: TGLsizeiptr); overload; inline;
  815. procedure SetBufferIndexedBinding(const Value: Cardinal; ATarget: TGLBufferBindingTarget; AIndex: Cardinal;
  816. AOffset: TGLintptr; ARangeSize: TGLsizeiptr); overload; inline;
  817. // Default values to be used when a vertex array is not used for that attribute
  818. property CurrentVertexAttrib[Index: Integer]: TGLVector read GetCurrentVertexAttrib write SetCurrentVertexAttrib;
  819. // Enables/disables program point size
  820. property EnableProgramPointSize: TGLboolean read FEnableProgramPointSize write SetEnableProgramPointSize;
  821. // Currently bound transform feedbac buffer
  822. property TransformFeedbackBufferBinding: Cardinal read FTransformFeedbackBufferBinding
  823. write SetTransformFeedbackBufferBinding;
  824. // Line smooth hint
  825. property LineSmoothHint: TGLHintType read FLineSmoothHint write SetLineSmoothHint;
  826. // Polygon smooth hint
  827. property PolygonSmoothHint: TGLHintType read FPolygonSmoothHint write SetPolygonSmoothHint;
  828. // Texture compression hint
  829. property TextureCompressionHint: TGLHintType read FTextureCompressionHint write SetTextureCompressionHint;
  830. // Fragment shader derivitive hint
  831. property FragmentShaderDerivitiveHint: TGLHintType read FFragmentShaderDerivitiveHint write SetFragmentShaderDerivitiveHint;
  832. property MultisampleFilterHint: TGLHintType read FMultisampleFilterHint write SetMultisampleFilterHint;
  833. // Current queries. Misc
  834. property CurrentQuery[Index: TGLQueryType]: Cardinal read GetCurrentQuery;
  835. // Begins a query of "Target" type. "Value" must be a valid query object
  836. procedure BeginQuery(const target: TGLQueryType; const Value: Cardinal); inline;
  837. // Ends current query of type "Target"
  838. procedure EndQuery(const target: TGLQueryType); inline;
  839. (* The buffer currently bound to the copy read buffer binding point, this
  840. is an extra binding point provided so that you don't need to overwrite
  841. other binding points to copy between buffers. *)
  842. property CopyReadBufferBinding: Cardinal read FCopyReadBufferBinding write SetCopyReadBufferBinding;
  843. (* The buffer currently bound to the copy write buffer binding point, this
  844. is an extra binding point provided so that you don't need to overwrite
  845. other binding points to copy between buffers. *)
  846. property CopyWriteBufferBinding: Cardinal read FCopyWriteBufferBinding write SetCopyWriteBufferBinding;
  847. // Enables/Disables seamless texture cube maps
  848. property EnableTextureCubeMapSeamless: TGLboolean read FEnableTextureCubeMapSeamless write SetEnableTextureCubeMapSeamless;
  849. // Indicates the current presence within the list
  850. property InsideList: Boolean read FInsideList;
  851. // Begin new display list
  852. procedure NewList(list: Cardinal; mode: Cardinal); inline;
  853. // End display list
  854. procedure EndList; inline;
  855. // Call display list
  856. procedure CallList(list: Cardinal); inline;
  857. // Defines the OpenGL texture matrix. Assumed texture mode is GL_MODELVIEW.
  858. procedure SetTextureMatrix(const matrix: TGLMatrix); inline;
  859. procedure ResetTextureMatrix; inline;
  860. procedure ResetAllTextureMatrix; inline;
  861. // note: needs to change to per draw-buffer
  862. procedure SetColorWriting(flag: Boolean); inline;
  863. // Inverts front face winding (CCW/CW)
  864. procedure InvertFrontFace; inline;
  865. // read only properties
  866. property States: TGLStates read FStates;
  867. // True for ignore deprecated and removed features in OpenGL 3x
  868. (* property ForwardContext: Boolean read FForwardContext write SetForwardContext; *)
  869. end;
  870. type
  871. TStateRecord = record
  872. GLConst: Cardinal;
  873. GLDeprecated: Boolean;
  874. end;
  875. const
  876. {$WARN SYMBOL_DEPRECATED OFF}
  877. cGLStateTypeToGLEnum: array [TGLStateType] of Cardinal = (
  878. GL_CURRENT_BIT, GL_POINT_BIT, GL_LINE_BIT, GL_POLYGON_BIT,
  879. GL_POLYGON_STIPPLE_BIT, GL_PIXEL_MODE_BIT, GL_LIGHTING_BIT, GL_FOG_BIT,
  880. GL_DEPTH_BUFFER_BIT, GL_ACCUM_BUFFER_BIT, GL_STENCIL_BUFFER_BIT,
  881. GL_VIEWPORT_BIT, GL_TRANSFORM_BIT, GL_ENABLE_BIT, GL_COLOR_BUFFER_BIT,
  882. GL_HINT_BIT, GL_EVAL_BIT, GL_LIST_BIT, GL_TEXTURE_BIT, GL_SCISSOR_BIT,
  883. GL_MULTISAMPLE_BIT);
  884. {$WARN SYMBOL_DEPRECATED ON}
  885. cGLStateToGLEnum: array[TGLState] of TStateRecord =
  886. ((GLConst: GL_ALPHA_TEST; GLDeprecated: True),
  887. (GLConst: GL_AUTO_NORMAL; GLDeprecated: True),
  888. (GLConst: GL_BLEND; GLDeprecated: False),
  889. (GLConst: GL_COLOR_MATERIAL; GLDeprecated: True),
  890. (GLConst: GL_CULL_FACE; GLDeprecated: False),
  891. (GLConst: GL_DEPTH_TEST; GLDeprecated: False),
  892. (GLConst: GL_DITHER; GLDeprecated: False),
  893. (GLConst: GL_FOG; GLDeprecated: True),
  894. (GLConst: GL_LIGHTING; GLDeprecated: True),
  895. (GLConst: GL_LINE_SMOOTH; GLDeprecated: True),
  896. (GLConst: GL_LINE_STIPPLE; GLDeprecated: True),
  897. (GLConst: GL_INDEX_LOGIC_OP; GLDeprecated: True),
  898. (GLConst: GL_COLOR_LOGIC_OP; GLDeprecated: False),
  899. (GLConst: GL_NORMALIZE; GLDeprecated: True),
  900. (GLConst: GL_POINT_SMOOTH; GLDeprecated: True),
  901. (GLConst: GL_POINT_SPRITE; GLDeprecated: True),
  902. (GLConst: GL_POLYGON_SMOOTH; GLDeprecated: True),
  903. (GLConst: GL_POLYGON_STIPPLE; GLDeprecated: True),
  904. (GLConst: GL_SCISSOR_TEST; GLDeprecated: False),
  905. (GLConst: GL_STENCIL_TEST; GLDeprecated: False),
  906. (GLConst: GL_POLYGON_OFFSET_POINT; GLDeprecated: False),
  907. (GLConst: GL_POLYGON_OFFSET_LINE; GLDeprecated: False),
  908. (GLConst: GL_POLYGON_OFFSET_FILL; GLDeprecated: False),
  909. (GLConst: GL_DEPTH_CLAMP; GLDeprecated: False)
  910. );
  911. cGLTexTypeToGLEnum: array[TGLTextureTarget] of Cardinal =
  912. (0, GL_TEXTURE_1D, GL_TEXTURE_2D, GL_TEXTURE_3D, GL_TEXTURE_1D_ARRAY,
  913. GL_TEXTURE_2D_ARRAY, GL_TEXTURE_RECTANGLE, GL_TEXTURE_BUFFER,
  914. GL_TEXTURE_CUBE_MAP, GL_TEXTURE_2D_MULTISAMPLE,
  915. GL_TEXTURE_2D_MULTISAMPLE_ARRAY, GL_TEXTURE_CUBE_MAP_ARRAY);
  916. cGLQueryTypeToGLEnum: array[TGLQueryType] of Cardinal =
  917. (GL_SAMPLES_PASSED, GL_PRIMITIVES_GENERATED,
  918. GL_TRANSFORM_FEEDBACK_PRIMITIVES_WRITTEN,
  919. GL_TIME_ELAPSED, GL_ANY_SAMPLES_PASSED);
  920. cGLStencilOpToGLEnum: array[TGLStencilOp] of Cardinal =
  921. (GL_KEEP, GL_ZERO, GL_REPLACE, GL_INCR, GL_DECR, GL_INVERT, GL_INCR_WRAP,
  922. GL_DECR_WRAP);
  923. cGLLogicOpToGLEnum: array[TGLLogicOp] of Cardinal =
  924. (GL_CLEAR, GL_AND, GL_AND_REVERSE, GL_COPY, GL_AND_INVERTED, GL_NOOP,
  925. GL_XOR, GL_OR, GL_NOR, GL_EQUIV, GL_INVERT, GL_OR_REVERSE,
  926. GL_COPY_INVERTED, GL_OR_INVERTED, GL_NAND, GL_SET);
  927. cGLComparisonFunctionToGLEnum: array[TGLComparisonFunction] of Cardinal =
  928. (GL_NEVER, GL_ALWAYS, GL_LESS, GL_LEQUAL, GL_EQUAL, GL_GREATER,
  929. GL_NOTEQUAL, GL_GEQUAL);
  930. cGLBlendFunctionToGLEnum: array[TGLBlendFunction] of Cardinal =
  931. (GL_ZERO, GL_ONE, GL_SRC_COLOR, GL_ONE_MINUS_SRC_COLOR, GL_DST_COLOR,
  932. GL_ONE_MINUS_DST_COLOR, GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA,
  933. GL_DST_ALPHA, GL_ONE_MINUS_DST_ALPHA, GL_CONSTANT_COLOR,
  934. GL_ONE_MINUS_CONSTANT_COLOR, GL_CONSTANT_ALPHA,
  935. GL_ONE_MINUS_CONSTANT_ALPHA, GL_SRC_ALPHA_SATURATE {valid for src only});
  936. cGLBlendEquationToGLEnum: array[TGLBlendEquation] of Cardinal =
  937. (GL_FUNC_ADD, GL_FUNC_SUBTRACT, GL_FUNC_REVERSE_SUBTRACT, GL_MIN,
  938. GL_MAX);
  939. cGLFaceWindingToGLEnum: array[TGLFaceWinding] of Cardinal =
  940. (GL_CCW, GL_CW);
  941. cGLPolygonModeToGLEnum: array[TGLPolygonMode] of Cardinal =
  942. (GL_FILL, GL_LINE, GL_POINT);
  943. cGLCullFaceModeToGLEnum: array[TGLCullFaceMode] of Cardinal =
  944. (GL_FRONT, GL_BACK, GL_FRONT_AND_BACK);
  945. cGLHintToGLEnum: array[TGLHintType] of Cardinal =
  946. (GL_DONT_CARE, GL_FASTEST, GL_NICEST);
  947. cGLBufferBindingTarget: array[TGLBufferBindingTarget] of Cardinal =
  948. (GL_UNIFORM_BUFFER, GL_TRANSFORM_FEEDBACK_BUFFER);
  949. implementation //------------------------------------------------------
  950. uses
  951. GLS.Context;
  952. // ------------------
  953. // ------------------ TGLStateCache ------------------
  954. // ------------------
  955. procedure TGLStateCache.BeginQuery(const target: TGLQueryType; const Value: Cardinal);
  956. begin
  957. Assert(FCurrentQuery[target] = 0, 'Can only have one query (of each type)' + ' running at a time');
  958. // Assert(glIsQuery(Value), 'Not a valid query');
  959. // if Value<>FCurrentQuery[Target] then
  960. begin
  961. FCurrentQuery[target] := Value;
  962. gl.BeginQuery(cGLQueryTypeToGLEnum[target], Value);
  963. end;
  964. end;
  965. constructor TGLStateCache.Create;
  966. var
  967. I: Integer;
  968. begin
  969. inherited;
  970. SetLength(FListStates, $FFFFF);
  971. FCurrentList := 0;
  972. // Material colors
  973. FFrontBackColors[0][0] := clrBlack;
  974. FFrontBackColors[0][1] := clrGray20;
  975. FFrontBackColors[0][2] := clrGray80;
  976. FFrontBackColors[0][3] := clrBlack;
  977. FFrontBackShininess[0] := 0;
  978. FFrontBackColors[1][0] := clrBlack;
  979. FFrontBackColors[1][1] := clrGray20;
  980. FFrontBackColors[1][2] := clrGray80;
  981. FFrontBackColors[1][3] := clrBlack;
  982. FFrontBackShininess[1] := 0;
  983. FAlphaFunc := cfAlways;
  984. // Lighting
  985. FFFPLight := True;
  986. FMaxLights := 0;
  987. FLightNumber := 0;
  988. for I := High(FLightEnabling) downto 0 do
  989. begin
  990. FLightEnabling[I] := False;
  991. FLightIndices[I] := 0;
  992. FLightStates.Position[I] := NullHmgVector;
  993. FLightStates.Ambient[I] := clrBlack;
  994. FLightStates.Diffuse[I] := clrBlack;
  995. FLightStates.Specular[I] := clrBlack;
  996. FLightStates.SpotDirection[I] := VectorMake(0.0, 0.0, -1.0, 0.0);
  997. FSpotCutoff[I] := 180.0;
  998. FLightStates.SpotCosCutoffExponent[I].X := -1;
  999. FLightStates.SpotCosCutoffExponent[I].Y := 0;
  1000. FLightStates.Attenuation[I] := NullHmgVector;
  1001. end;
  1002. FLightStates.Diffuse[0] := clrWhite;
  1003. FLightStates.Specular[0] := clrWhite;
  1004. for I := High(FTextureMatrixIsIdentity) downto 0 do
  1005. FTextureMatrixIsIdentity[I] := False;
  1006. // FForwardContext := False;
  1007. // Vertex Array Data state
  1008. FVertexArrayBinding := 0;
  1009. FTextureBufferBinding := 0;
  1010. // Transformation state
  1011. // FViewPort := Rect(0,0,0,0); // (0, 0, Width, Height)
  1012. FDepthRange[0] := 0.0;
  1013. FDepthRange[1] := 1.0;
  1014. FillChar(FEnableClipDistance, sizeof(FEnableClipDistance), $00);
  1015. FEnableDepthClamp := False;
  1016. // Coloring state
  1017. FClampReadColor := GL_FIXED_ONLY;
  1018. FProvokingVertex := GL_LAST_VERTEX_CONVENTION;
  1019. // Rasterization state
  1020. FPointSize := 1.0;
  1021. FPointFadeThresholdSize := 1.0;
  1022. FPointSpriteCoordOrigin := GL_UPPER_LEFT;
  1023. FLineWidth := 1.0;
  1024. FLineStippleFactor := 1;
  1025. FLineStipplePattern := $FFFF;
  1026. FEnableLineSmooth := False;
  1027. FEnableCullFace := False;
  1028. FCullFaceMode := cmBack;
  1029. FFrontFace := fwCounterClockWise;
  1030. FEnablePolygonSmooth := False;
  1031. FPolygonMode := pmFill;
  1032. FPolygonOffsetFactor := 0.0;
  1033. FPolygonOffsetUnits := 0.0;
  1034. FEnablePolygonOffsetPoint := False;
  1035. FEnablePolygonOffsetLine := False;
  1036. FEnablePolygonOffsetFill := False;
  1037. // Multisample state
  1038. FEnableMultisample := True;
  1039. FEnableSampleAlphaToCoverage := False;
  1040. FEnableSampleAlphaToOne := False;
  1041. FEnableSampleCoverage := False;
  1042. FSampleCoverageValue := 1.0;
  1043. FSampleCoverageInvert := False;
  1044. FEnableSampleMask := False;
  1045. FillChar(FSampleMaskValue, sizeof(FSampleMaskValue), $FF);
  1046. // Texture state
  1047. FillChar(FTextureBinding, sizeof(FTextureBinding), $00);
  1048. FillChar(FActiveTextureEnabling, sizeof(FActiveTextureEnabling), $00);
  1049. // Active texture state
  1050. FActiveTexture := 0;
  1051. // Pixel operation state
  1052. FEnableScissorTest := False;
  1053. // FScissorBox := Rect(0, 0, Width, Height);
  1054. FEnableStencilTest := False;
  1055. FStencilFunc := cfAlways;
  1056. FStencilValueMask := $FFFFFFFF;
  1057. FStencilRef := 0;
  1058. FStencilFail := soKeep;
  1059. FStencilPassDepthFail := soKeep;
  1060. FStencilPassDepthPass := soKeep;
  1061. FStencilBackFunc := cfAlways;
  1062. FStencilBackValueMask := $FFFFFFFF;
  1063. FStencilBackRef := 0;
  1064. FStencilBackFail := soKeep;
  1065. FStencilBackPassDepthPass := soKeep;
  1066. FStencilBackPassDepthFail := soKeep;
  1067. FEnableDepthTest := False;
  1068. FDepthFunc := cfLess;
  1069. FillChar(FEnableBlend, sizeof(FEnableBlend), $0);
  1070. FBlendSrcRGB := bfOne;
  1071. FBlendSrcAlpha := bfOne;
  1072. FBlendDstRGB := bfZero;
  1073. FBlendDstAlpha := bfZero;
  1074. FBlendEquationRGB := beAdd;
  1075. FBlendEquationAlpha := beAdd;
  1076. FBlendColor := NullHmgVector;
  1077. FEnableFramebufferSRGB := False;
  1078. FEnableDither := True;
  1079. FEnableColorLogicOp := False;
  1080. FLogicOpMode := loCopy;
  1081. // Framebuffer control state
  1082. // for I := 0 to Length(FColorWriteMask) - 1 do
  1083. // FColorWriteMask[i] := [ccRed, ccGreen, ccBlue, ccAlpha];
  1084. FillChar(FColorWriteMask, sizeof(FColorWriteMask), $F);
  1085. FDepthWriteMask := True;
  1086. FStencilWriteMask := $FFFFFFFF;
  1087. FStencilBackWriteMask := $FFFFFFFF;
  1088. FColorClearValue := NullHmgVector;
  1089. FDepthClearValue := 1.0;
  1090. FStencilClearValue := 0;
  1091. // Framebuffer state
  1092. FDrawFrameBuffer := 0;
  1093. FReadFrameBuffer := 0;
  1094. // Renderbuffer state
  1095. FRenderBuffer := 0;
  1096. // Pixels state
  1097. FUnpackSwapBytes := False;
  1098. FUnpackLSBFirst := False;
  1099. FUnpackImageHeight := 0;
  1100. FUnpackSkipImages := 0;
  1101. FUnpackRowLength := 0;
  1102. FUnpackSkipRows := 0;
  1103. FUnpackSkipPixels := 0;
  1104. FUnpackAlignment := 4;
  1105. FPackSwapBytes := False;
  1106. FPackLSBFirst := False;
  1107. FPackImageHeight := 0;
  1108. FPackSkipImages := 0;
  1109. FPackRowLength := 0;
  1110. FPackSkipRows := 0;
  1111. FPackSkipPixels := 0;
  1112. FPackAlignment := 4;
  1113. FPixelPackBufferBinding := 0;
  1114. FPixelUnpackBufferBinding := 0;
  1115. // Program state
  1116. FCurrentProgram := 0;
  1117. FUniformBufferBinding := 0;
  1118. FillChar(FUBOStates[bbtUniform][0], SizeOf(FUBOStates), $00);
  1119. // Vector + Geometry Shader state
  1120. for I := 0 to Length(FCurrentVertexAttrib) - 1 do
  1121. FCurrentVertexAttrib[I] := NullHmgPoint;
  1122. FEnableProgramPointSize := False;
  1123. // Transform Feedback state
  1124. FTransformFeedbackBufferBinding := 0;
  1125. // Hints state
  1126. FTextureCompressionHint := hintDontCare;
  1127. FPolygonSmoothHint := hintDontCare;
  1128. FFragmentShaderDerivitiveHint := hintDontCare;
  1129. FLineSmoothHint := hintDontCare;
  1130. // Misc state
  1131. FillChar(FCurrentQuery, sizeof(FCurrentQuery), $00);
  1132. FCopyReadBufferBinding := 0;
  1133. FCopyWriteBufferBinding := 0;
  1134. FEnableTextureCubeMapSeamless := False;
  1135. FInsideList := False;
  1136. end;
  1137. destructor TGLStateCache.Destroy;
  1138. begin
  1139. inherited;
  1140. end;
  1141. procedure TGLStateCache.EndQuery(const target: TGLQueryType);
  1142. begin
  1143. Assert(FCurrentQuery[target] <> 0, 'No query running');
  1144. FCurrentQuery[target] := 0;
  1145. gl.EndQuery(cGLQueryTypeToGLEnum[target]);
  1146. end;
  1147. procedure TGLStateCache.Enable(const aState: TGLState);
  1148. begin
  1149. { if cGLStateToGLEnum[aState].GLDeprecated and FForwardContext then
  1150. exit; }
  1151. if not(aState in FStates) or FInsideList then
  1152. begin
  1153. if FInsideList then
  1154. Include(FListStates[FCurrentList], sttEnable)
  1155. else
  1156. Include(FStates, aState);
  1157. {$IFDEF USE_CACHE_MISS_CHECK}
  1158. if gl.IsEnabled(cGLStateToGLEnum[aState].GLConst) then
  1159. GLSLogger.LogError(strStateCashMissing + 'Enable');
  1160. {$ENDIF}
  1161. gl.Enable(cGLStateToGLEnum[aState].GLConst);
  1162. end;
  1163. end;
  1164. procedure TGLStateCache.Disable(const aState: TGLState);
  1165. begin
  1166. { if cGLStateToGLEnum[aState].GLDeprecated and FForwardContext then
  1167. exit; }
  1168. if (aState in FStates) or FInsideList then
  1169. begin
  1170. if FInsideList then
  1171. Include(FListStates[FCurrentList], sttEnable)
  1172. else
  1173. Exclude(FStates, aState);
  1174. {$IFDEF USE_CACHE_MISS_CHECK}
  1175. if not gl.IsEnabled(cGLStateToGLEnum[aState].GLConst) then
  1176. GLSLogger.LogError(strStateCashMissing + 'Disable');
  1177. {$ENDIF}
  1178. gl.Disable(cGLStateToGLEnum[aState].GLConst);
  1179. if aState = stColorMaterial then
  1180. if FInsideList then
  1181. Include(FListStates[FCurrentList], sttLighting)
  1182. else
  1183. begin
  1184. gl.Materialfv(GL_FRONT, GL_EMISSION, @FFrontBackColors[0][0]);
  1185. gl.Materialfv(GL_FRONT, GL_AMBIENT, @FFrontBackColors[0][1]);
  1186. gl.Materialfv(GL_FRONT, GL_DIFFUSE, @FFrontBackColors[0][2]);
  1187. gl.Materialfv(GL_FRONT, GL_SPECULAR, @FFrontBackColors[0][3]);
  1188. gl.Materiali(GL_FRONT, GL_SHININESS, FFrontBackShininess[0]);
  1189. gl.Materialfv(GL_BACK, GL_EMISSION, @FFrontBackColors[1][0]);
  1190. gl.Materialfv(GL_BACK, GL_AMBIENT, @FFrontBackColors[1][1]);
  1191. gl.Materialfv(GL_BACK, GL_DIFFUSE, @FFrontBackColors[1][2]);
  1192. gl.Materialfv(GL_BACK, GL_SPECULAR, @FFrontBackColors[1][3]);
  1193. gl.Materiali(GL_BACK, GL_SHININESS, FFrontBackShininess[1]);
  1194. end;
  1195. end;
  1196. end;
  1197. procedure TGLStateCache.PerformEnable(const aState: TGLState);
  1198. begin
  1199. { if cGLStateToGLEnum[aState].GLDeprecated and FForwardContext then
  1200. exit; }
  1201. Include(FStates, aState);
  1202. gl.Enable(cGLStateToGLEnum[aState].GLConst);
  1203. end;
  1204. procedure TGLStateCache.PerformDisable(const aState: TGLState);
  1205. begin
  1206. { if cGLStateToGLEnum[aState].GLDeprecated and FForwardContext then
  1207. exit; }
  1208. Exclude(FStates, aState);
  1209. gl.Disable(cGLStateToGLEnum[aState].GLConst);
  1210. end;
  1211. procedure TGLStateCache.PopAttrib;
  1212. begin
  1213. // TODO: replace with proper client side push/pop
  1214. gl.PopAttrib();
  1215. end;
  1216. procedure TGLStateCache.PushAttrib(const stateTypes: TGLStateTypes);
  1217. var
  1218. tempFlag: Cardinal;
  1219. I: Integer;
  1220. begin
  1221. // TODO: replace with proper client side push/pop
  1222. tempFlag := 0;
  1223. for I := Integer(Low(TGLStateType)) to Integer(high(TGLStateType)) do
  1224. begin
  1225. if TGLStateType(I) in stateTypes then
  1226. begin
  1227. tempFlag := tempFlag or cGLStateTypeToGLEnum[TGLStateType(I)];
  1228. end;
  1229. end;
  1230. gl.PushAttrib(tempFlag);
  1231. end;
  1232. procedure TGLStateCache.SetGLMaterialColors(const aFace: TGLCullFaceMode;
  1233. const emission, ambient, diffuse, specular: TGLVector;
  1234. const shininess: Integer);
  1235. var
  1236. I: Integer;
  1237. currentFace: Cardinal;
  1238. begin
  1239. { if FForwardContext then
  1240. exit; }
  1241. Assert((aFace = cmFront) or (aFace = cmBack), 'Only cmFront or cmBack supported');
  1242. I := Integer(aFace);
  1243. currentFace := cGLCullFaceModeToGLEnum[aFace];
  1244. if FInsideList then
  1245. begin
  1246. gl.Materiali(currentFace, GL_SHININESS, shininess);
  1247. gl.Materialfv(currentFace, GL_EMISSION, @emission);
  1248. gl.Materialfv(currentFace, GL_AMBIENT, @Ambient);
  1249. gl.Materialfv(currentFace, GL_DIFFUSE, @Diffuse);
  1250. gl.Materialfv(currentFace, GL_SPECULAR, @Specular);
  1251. Include(FListStates[FCurrentList], sttLighting);
  1252. end
  1253. else
  1254. begin
  1255. if (FFrontBackShininess[I] <> shininess) then
  1256. begin
  1257. gl.Materiali(currentFace, GL_SHININESS, shininess);
  1258. FFrontBackShininess[I] := shininess;
  1259. end;
  1260. if not AffineVectorEquals(FFrontBackColors[I][0], emission) then
  1261. begin
  1262. gl.Materialfv(currentFace, GL_EMISSION, @emission);
  1263. SetVector(FFrontBackColors[I][0], emission);
  1264. end;
  1265. if not AffineVectorEquals(FFrontBackColors[I][1], Ambient) then
  1266. begin
  1267. gl.Materialfv(currentFace, GL_AMBIENT, @Ambient);
  1268. SetVector(FFrontBackColors[I][1], Ambient);
  1269. end;
  1270. if not VectorEquals(FFrontBackColors[I][2], Diffuse) then
  1271. begin
  1272. gl.Materialfv(currentFace, GL_DIFFUSE, @Diffuse);
  1273. SetVector(FFrontBackColors[I][2], Diffuse);
  1274. end;
  1275. if not AffineVectorEquals(FFrontBackColors[I][3], Specular) then
  1276. begin
  1277. gl.Materialfv(currentFace, GL_SPECULAR, @Specular);
  1278. SetVector(FFrontBackColors[I][3], Specular);
  1279. end;
  1280. end;
  1281. end;
  1282. procedure TGLStateCache.SetGLMaterialAlphaChannel(const aFace: Cardinal; const alpha: TGLfloat);
  1283. var
  1284. I: Integer;
  1285. color: TVector4f;
  1286. begin
  1287. { if FForwardContext then Exit; }
  1288. if not(stLighting in FStates) then
  1289. begin
  1290. // We need a temp variable, because FColor is cauched.
  1291. gl.GetFloatv(GL_CURRENT_COLOR, @color);
  1292. color.W := alpha;
  1293. gl.Color4fv(@color);
  1294. end
  1295. else
  1296. begin
  1297. I := aFace - GL_FRONT;
  1298. if (FFrontBackColors[I][2].W <> alpha) or FInsideList then
  1299. begin
  1300. if FInsideList then
  1301. begin
  1302. Include(FListStates[FCurrentList], sttLighting);
  1303. gl.Materialfv(aFace, GL_DIFFUSE, @FFrontBackColors[I][2]);
  1304. end
  1305. else
  1306. begin
  1307. FFrontBackColors[I][2].W := alpha;
  1308. gl.Materialfv(aFace, GL_DIFFUSE, @FFrontBackColors[I][2]);
  1309. end;
  1310. end;
  1311. end;
  1312. end;
  1313. procedure TGLStateCache.SetGLMaterialDiffuseColor(const aFace: Cardinal; const Diffuse: TGLVector);
  1314. var
  1315. I: Integer;
  1316. begin
  1317. { if FForwardContext then Exit; }
  1318. if not(stLighting in FStates) then
  1319. begin
  1320. gl.Color4fv(@Diffuse);
  1321. end
  1322. else
  1323. begin
  1324. //
  1325. I := aFace - GL_FRONT;
  1326. if (not VectorEquals(FFrontBackColors[I][2], Diffuse)) or FInsideList then
  1327. begin
  1328. if FInsideList then
  1329. begin
  1330. Include(FListStates[FCurrentList], sttLighting);
  1331. gl.Materialfv(aFace, GL_DIFFUSE, @FFrontBackColors[I][2]);
  1332. end
  1333. else
  1334. begin
  1335. FFrontBackColors[I][2] := Diffuse;
  1336. gl.Materialfv(aFace, GL_DIFFUSE, @Diffuse);
  1337. end;
  1338. end;
  1339. end;
  1340. end;
  1341. procedure TGLStateCache.SetActiveTexture(const Value: TGLint);
  1342. begin
  1343. if gl.ARB_multitexture then
  1344. if (Value <> FActiveTexture) or FInsideList then
  1345. begin
  1346. if FInsideList then
  1347. Include(FListStates[FCurrentList], sttTexture)
  1348. else
  1349. FActiveTexture := Value;
  1350. gl.ActiveTexture(GL_TEXTURE0 + Value);
  1351. end;
  1352. end;
  1353. procedure TGLStateCache.SetVertexArrayBinding(const Value: Cardinal);
  1354. begin
  1355. if Value <> FVertexArrayBinding then
  1356. begin
  1357. FVertexArrayBinding := Value;
  1358. gl.BindVertexArray(Value);
  1359. end;
  1360. end;
  1361. function TGLStateCache.GetArrayBufferBinding: Cardinal;
  1362. begin
  1363. Result := FArrayBufferBinding;
  1364. end;
  1365. procedure TGLStateCache.SetArrayBufferBinding(const Value: Cardinal);
  1366. begin
  1367. if (Value <> FArrayBufferBinding) or (FVertexArrayBinding <> 0) then
  1368. begin
  1369. FArrayBufferBinding := Value;
  1370. gl.BindBuffer(GL_ARRAY_BUFFER, Value);
  1371. end;
  1372. end;
  1373. function TGLStateCache.GetElementBufferBinding: Cardinal;
  1374. begin
  1375. Result := FElementBufferBinding
  1376. end;
  1377. procedure TGLStateCache.SetElementBufferBinding(const Value: Cardinal);
  1378. begin
  1379. if (Value <> FElementBufferBinding) or (FVertexArrayBinding <> 0) then
  1380. begin
  1381. FElementBufferBinding := Value;
  1382. gl.BindBuffer(GL_ELEMENT_ARRAY_BUFFER, Value);
  1383. end;
  1384. end;
  1385. function TGLStateCache.GetEnablePrimitiveRestart: TGLboolean;
  1386. begin
  1387. Result := FEnablePrimitiveRestart;
  1388. end;
  1389. procedure TGLStateCache.SetEnablePrimitiveRestart(const enabled: TGLboolean);
  1390. begin
  1391. if enabled <> FEnablePrimitiveRestart then
  1392. begin
  1393. FEnablePrimitiveRestart := enabled;
  1394. if GL.NV_primitive_restart then
  1395. begin
  1396. if enabled then
  1397. gl.EnableClientState(GL_PRIMITIVE_RESTART_NV)
  1398. else
  1399. gl.DisableClientState(GL_PRIMITIVE_RESTART_NV);
  1400. end
  1401. else
  1402. begin
  1403. if enabled then
  1404. gl.Enable(GL_PRIMITIVE_RESTART)
  1405. else
  1406. gl.Disable(GL_PRIMITIVE_RESTART);
  1407. end;
  1408. end;
  1409. end;
  1410. function TGLStateCache.GetPrimitiveRestartIndex: Cardinal;
  1411. begin
  1412. Result := FPrimitiveRestartIndex;
  1413. end;
  1414. procedure TGLStateCache.SetPrimitiveRestartIndex(const index: Cardinal);
  1415. begin
  1416. if index <> FPrimitiveRestartIndex then
  1417. begin
  1418. if gl.NV_primitive_restart then
  1419. begin
  1420. FPrimitiveRestartIndex := index;
  1421. gl.PrimitiveRestartIndex(index)
  1422. end;
  1423. end;
  1424. end;
  1425. procedure TGLStateCache.SetEnableProgramPointSize(const Value: TGLboolean);
  1426. begin
  1427. if Value <> FEnableProgramPointSize then
  1428. begin
  1429. FEnableProgramPointSize := Value;
  1430. if Value then
  1431. gl.Enable(GL_PROGRAM_POINT_SIZE)
  1432. else
  1433. gl.Disable(GL_PROGRAM_POINT_SIZE);
  1434. end;
  1435. end;
  1436. procedure TGLStateCache.SetBlendColor(const Value: TGLVector);
  1437. begin
  1438. if not VectorEquals(Value, FBlendColor) or FInsideList then
  1439. begin
  1440. if FInsideList then
  1441. Include(FListStates[FCurrentList], sttColorBuffer)
  1442. else
  1443. FBlendColor := Value;
  1444. gl.BlendColor(Value.X, Value.Y, Value.Z, Value.W);
  1445. end;
  1446. end;
  1447. procedure TGLStateCache.SetBlendEquationSeparate(const modeRGB, modeAlpha: TGLBlendEquation);
  1448. begin
  1449. if (modeRGB <> FBlendEquationRGB) or (modeAlpha <> FBlendEquationAlpha) or FInsideList then
  1450. begin
  1451. FBlendEquationRGB := modeRGB;
  1452. FBlendEquationAlpha := modeAlpha;
  1453. gl.BlendEquationSeparate(cGLBlendEquationToGLEnum[modeRGB], cGLBlendEquationToGLEnum[modeAlpha]);
  1454. end;
  1455. if FInsideList then
  1456. Include(FListStates[FCurrentList], sttColorBuffer);
  1457. end;
  1458. procedure TGLStateCache.SetBlendEquation(const mode: TGLBlendEquation);
  1459. begin
  1460. if (mode <> FBlendEquationRGB) or (mode <> FBlendEquationAlpha) or FInsideList then
  1461. begin
  1462. if FInsideList then
  1463. Include(FListStates[FCurrentList], sttColorBuffer)
  1464. else
  1465. begin
  1466. FBlendEquationRGB := mode;
  1467. FBlendEquationAlpha := mode;
  1468. end;
  1469. gl.BlendEquation(cGLBlendEquationToGLEnum[mode]);
  1470. end;
  1471. end;
  1472. procedure TGLStateCache.SetBlendFunc(const Src: TGLBlendFunction; const Dst: TGLDstBlendFunction);
  1473. begin
  1474. if (Src <> FBlendSrcRGB) or (Dst <> FBlendDstRGB) or FInsideList then
  1475. begin
  1476. if FInsideList then
  1477. Include(FListStates[FCurrentList], sttColorBuffer)
  1478. else
  1479. begin
  1480. FBlendSrcRGB := Src;
  1481. FBlendDstRGB := Dst;
  1482. FBlendSrcAlpha := Src;
  1483. FBlendSrcAlpha := Dst;
  1484. end;
  1485. gl.BlendFunc(cGLBlendFunctionToGLEnum[Src], cGLBlendFunctionToGLEnum[Dst]);
  1486. end;
  1487. end;
  1488. procedure TGLStateCache.SetBlendFuncSeparate(const SrcRGB: TGLBlendFunction;
  1489. const DstRGB: TGLDstBlendFunction; const SrcAlpha: TGLBlendFunction; const DstAlpha: TGLDstBlendFunction);
  1490. begin
  1491. if (SrcRGB <> FBlendSrcRGB) or (DstRGB <> FBlendDstRGB) or
  1492. (SrcAlpha <> FBlendSrcAlpha) or (DstAlpha <> FBlendDstAlpha)
  1493. or FInsideList then
  1494. begin
  1495. if FInsideList then
  1496. Include(FListStates[FCurrentList], sttColorBuffer)
  1497. else
  1498. begin
  1499. FBlendSrcRGB := SrcRGB;
  1500. FBlendDstRGB := DstRGB;
  1501. FBlendSrcAlpha := SrcAlpha;
  1502. FBlendDstAlpha := DstAlpha;
  1503. end;
  1504. gl.BlendFuncSeparate(
  1505. cGLBlendFunctionToGLEnum[SrcRGB],
  1506. cGLBlendFunctionToGLEnum[DstRGB],
  1507. cGLBlendFunctionToGLEnum[SrcAlpha],
  1508. cGLBlendFunctionToGLEnum[DstAlpha]);
  1509. end;
  1510. end;
  1511. procedure TGLStateCache.SetClampReadColor(const Value: Cardinal);
  1512. begin
  1513. if (Value <> FClampReadColor) or FInsideList then
  1514. begin
  1515. if FInsideList then
  1516. Include(FListStates[FCurrentList], sttColorBuffer)
  1517. else
  1518. FClampReadColor := Value;
  1519. gl.ClampColor(GL_CLAMP_READ_COLOR, Value);
  1520. end;
  1521. end;
  1522. procedure TGLStateCache.SetColorWriteMask(index: Integer; const Value: TGLColorMask);
  1523. begin
  1524. if FColorWriteMask[Index] <> Value then
  1525. begin
  1526. FColorWriteMask[Index] := Value;
  1527. gl.ColorMaski(Index, ccRed in Value, ccGreen in Value, ccBlue in Value, ccAlpha in Value);
  1528. end;
  1529. end;
  1530. procedure TGLStateCache.SetCopyReadBufferBinding(const Value: Cardinal);
  1531. begin
  1532. if Value <> FCopyReadBufferBinding then
  1533. begin
  1534. FCopyReadBufferBinding := Value;
  1535. gl.BindBuffer(GL_COPY_READ_BUFFER, Value);
  1536. end;
  1537. end;
  1538. procedure TGLStateCache.SetCopyWriteBufferBinding(const Value: Cardinal);
  1539. begin
  1540. if Value <> FCopyWriteBufferBinding then
  1541. begin
  1542. FCopyWriteBufferBinding := Value;
  1543. gl.BindBuffer(GL_COPY_WRITE_BUFFER, Value);
  1544. end;
  1545. end;
  1546. procedure TGLStateCache.SetCullFaceMode(const Value: TGLCullFaceMode);
  1547. begin
  1548. if (Value <> FCullFaceMode) or FInsideList then
  1549. begin
  1550. if FInsideList then
  1551. Include(FListStates[FCurrentList], sttPolygon)
  1552. else
  1553. FCullFaceMode := Value;
  1554. gl.CullFace(cGLCullFaceModeToGLEnum[Value]);
  1555. end;
  1556. end;
  1557. procedure TGLStateCache.SetCurrentProgram(const Value: Cardinal);
  1558. begin
  1559. if Value <> FCurrentProgram then
  1560. begin
  1561. FCurrentProgram := Value;
  1562. gl.UseProgram(Value);
  1563. end;
  1564. end;
  1565. procedure TGLStateCache.SetTextureBufferBinding(const Value: Cardinal);
  1566. begin
  1567. if Value <> FTextureBufferBinding then
  1568. begin
  1569. FTextureBufferBinding := Value;
  1570. gl.BindBuffer(GL_TEXTURE_BUFFER, Value);
  1571. end;
  1572. end;
  1573. procedure TGLStateCache.SetCurrentVertexAttrib(index: Integer; const Value: TGLVector);
  1574. begin
  1575. if not VectorEquals(Value, FCurrentVertexAttrib[Index]) then
  1576. begin
  1577. FCurrentVertexAttrib[Index] := Value;
  1578. gl.VertexAttrib4fv(Index, @Value.X);
  1579. end;
  1580. end;
  1581. procedure TGLStateCache.SetDepthClearValue(const Value: TGLfloat);
  1582. begin
  1583. if (Value <> FDepthClearValue) or FInsideList then
  1584. begin
  1585. if FInsideList then
  1586. Include(FListStates[FCurrentList], sttDepthBuffer)
  1587. else
  1588. FDepthClearValue := Value;
  1589. gl.ClearDepth(Value);
  1590. end;
  1591. end;
  1592. procedure TGLStateCache.SetDepthFunc(const Value: TGLDepthFunction);
  1593. begin
  1594. if (Value <> FDepthFunc) or FInsideList then
  1595. begin
  1596. if FInsideList then
  1597. Include(FListStates[FCurrentList], sttDepthBuffer)
  1598. else
  1599. FDepthFunc := Value;
  1600. gl.DepthFunc(cGLComparisonFunctionToGLEnum[Value]);
  1601. end;
  1602. end;
  1603. procedure TGLStateCache.SetDepthRange(const ZNear, ZFar: TGLclampd);
  1604. begin
  1605. if (ZNear <> FDepthRange[0]) or (ZFar <> FDepthRange[1]) or FInsideList then
  1606. begin
  1607. if FInsideList then
  1608. Include(FListStates[FCurrentList], sttViewport)
  1609. else
  1610. begin
  1611. FDepthRange[0] := ZNear;
  1612. FDepthRange[1] := ZFar;
  1613. end;
  1614. gl.DepthRange(ZNear, ZFar);
  1615. end;
  1616. end;
  1617. procedure TGLStateCache.SetDepthRangeFar(const Value: TGLclampd);
  1618. begin
  1619. if (Value <> FDepthRange[1]) or FInsideList then
  1620. begin
  1621. if FInsideList then
  1622. Include(FListStates[FCurrentList], sttViewport)
  1623. else
  1624. FDepthRange[1] := Value;
  1625. gl.DepthRange(FDepthRange[0], Value);
  1626. end;
  1627. end;
  1628. procedure TGLStateCache.SetDepthRangeNear(const Value: TGLclampd);
  1629. begin
  1630. if (Value <> FDepthRange[0]) or FInsideList then
  1631. begin
  1632. if FInsideList then
  1633. Include(FListStates[FCurrentList], sttViewport)
  1634. else
  1635. FDepthRange[0] := Value;
  1636. gl.DepthRange(Value, FDepthRange[1]);
  1637. end;
  1638. end;
  1639. procedure TGLStateCache.SetDepthWriteMask(const Value: TGLboolean);
  1640. begin
  1641. if (Value <> FDepthWriteMask) or FInsideList then
  1642. begin
  1643. if FInsideList then
  1644. Include(FListStates[FCurrentList], sttDepthBuffer)
  1645. else
  1646. FDepthWriteMask := Value;
  1647. gl.DepthMask(Value);
  1648. end;
  1649. end;
  1650. procedure TGLStateCache.SetDrawFrameBuffer(const Value: Cardinal);
  1651. begin
  1652. if Value <> FDrawFrameBuffer then
  1653. begin
  1654. FDrawFrameBuffer := Value;
  1655. gl.BindFramebuffer(GL_DRAW_FRAMEBUFFER, Value);
  1656. end;
  1657. end;
  1658. procedure TGLStateCache.SetEnableBlend(index: Integer; const Value: TGLboolean);
  1659. begin
  1660. if FEnableBlend[Index] <> Value then
  1661. begin
  1662. FEnableBlend[Index] := Value;
  1663. if Value then
  1664. gl.Enablei(GL_BLEND, Index)
  1665. else
  1666. gl.Disablei(GL_BLEND, Index);
  1667. end;
  1668. end;
  1669. procedure TGLStateCache.SetEnableClipDistance(index: Cardinal; const Value: TGLboolean);
  1670. begin
  1671. if FEnableClipDistance[Index] <> Value then
  1672. begin
  1673. FEnableClipDistance[Index] := Value;
  1674. if Value then
  1675. gl.Enable(GL_CLIP_DISTANCE0 + Index)
  1676. else
  1677. gl.Disable(GL_CLIP_DISTANCE0 + Index);
  1678. end;
  1679. end;
  1680. procedure TGLStateCache.SetEnableColorLogicOp(const Value: TGLboolean);
  1681. begin
  1682. if Value <> FEnableColorLogicOp then
  1683. begin
  1684. FEnableColorLogicOp := Value;
  1685. if Value then
  1686. gl.Enable(GL_COLOR_LOGIC_OP)
  1687. else
  1688. gl.Disable(GL_COLOR_LOGIC_OP);
  1689. end;
  1690. end;
  1691. procedure TGLStateCache.SetEnableCullFace(const Value: TGLboolean);
  1692. begin
  1693. end;
  1694. procedure TGLStateCache.SetEnableDepthClamp(const enabled: TGLboolean);
  1695. begin
  1696. end;
  1697. procedure TGLStateCache.SetEnableDepthTest(const Value: TGLboolean);
  1698. begin
  1699. end;
  1700. procedure TGLStateCache.SetEnableDither(const Value: TGLboolean);
  1701. begin
  1702. end;
  1703. procedure TGLStateCache.SetEnableFramebufferSRGB(const Value: TGLboolean);
  1704. begin
  1705. end;
  1706. procedure TGLStateCache.SetEnableLineSmooth(const Value: TGLboolean);
  1707. begin
  1708. end;
  1709. procedure TGLStateCache.SetEnableMultisample(const Value: TGLboolean);
  1710. begin
  1711. end;
  1712. procedure TGLStateCache.SetEnablePolygonOffsetFill(const Value: TGLboolean);
  1713. begin
  1714. end;
  1715. procedure TGLStateCache.SetEnablePolygonOffsetLine(const Value: TGLboolean);
  1716. begin
  1717. end;
  1718. procedure TGLStateCache.SetEnablePolygonOffsetPoint(const Value: TGLboolean);
  1719. begin
  1720. end;
  1721. procedure TGLStateCache.SetEnablePolygonSmooth(const Value: TGLboolean);
  1722. begin
  1723. end;
  1724. procedure TGLStateCache.SetEnableSampleAlphaToCoverage(const Value: TGLboolean);
  1725. begin
  1726. if Value <> FEnableSampleAlphaToCoverage then
  1727. begin
  1728. FEnableSampleAlphaToCoverage := Value;
  1729. if Value then
  1730. gl.Enable(GL_SAMPLE_ALPHA_TO_COVERAGE)
  1731. else
  1732. gl.Disable(GL_SAMPLE_ALPHA_TO_COVERAGE);
  1733. end;
  1734. end;
  1735. procedure TGLStateCache.SetEnableSampleCoverage(const Value: TGLboolean);
  1736. begin
  1737. if Value <> FEnableSampleCoverage then
  1738. begin
  1739. FEnableSampleCoverage := Value;
  1740. if Value then
  1741. gl.Enable(GL_SAMPLE_COVERAGE)
  1742. else
  1743. gl.Disable(GL_SAMPLE_COVERAGE);
  1744. end;
  1745. end;
  1746. procedure TGLStateCache.SetEnableSampleMask(const Value: TGLboolean);
  1747. begin
  1748. if Value <> FEnableSampleMask then
  1749. begin
  1750. FEnableSampleMask := Value;
  1751. if Value then
  1752. gl.Enable(GL_SAMPLE_MASK)
  1753. else
  1754. gl.Disable(GL_SAMPLE_MASK);
  1755. end;
  1756. end;
  1757. procedure TGLStateCache.SetEnableSampleAlphaToOne(const Value: TGLboolean);
  1758. begin
  1759. if Value <> FEnableSampleAlphaToOne then
  1760. begin
  1761. FEnableSampleAlphaToOne := Value;
  1762. if Value then
  1763. gl.Enable(GL_SAMPLE_ALPHA_TO_ONE)
  1764. else
  1765. gl.Disable(GL_SAMPLE_ALPHA_TO_ONE);
  1766. end;
  1767. end;
  1768. procedure TGLStateCache.SetEnableScissorTest(const Value: TGLboolean);
  1769. begin
  1770. end;
  1771. procedure TGLStateCache.SetEnableStencilTest(const Value: TGLboolean);
  1772. begin
  1773. end;
  1774. procedure TGLStateCache.SetFragmentShaderDerivitiveHint(const Value: TGLHintType);
  1775. begin
  1776. if Value <> FFragmentShaderDerivitiveHint then
  1777. begin
  1778. if FInsideList then
  1779. Include(FListStates[FCurrentList], sttHint)
  1780. else
  1781. FFragmentShaderDerivitiveHint := Value;
  1782. gl.Hint(GL_FRAGMENT_SHADER_DERIVATIVE_HINT, cGLHintToGLEnum[Value]);
  1783. end;
  1784. end;
  1785. procedure TGLStateCache.SetMultisampleFilterHint(const Value: TGLHintType);
  1786. begin
  1787. if GL.NV_multisample_filter_hint then
  1788. if Value <> FMultisampleFilterHint then
  1789. begin
  1790. if FInsideList then
  1791. Include(FListStates[FCurrentList], sttHint)
  1792. else
  1793. FMultisampleFilterHint := Value;
  1794. gl.Hint(GL_MULTISAMPLE_FILTER_HINT_NV, cGLHintToGLEnum[Value]);
  1795. end;
  1796. end;
  1797. procedure TGLStateCache.SetFrameBuffer(const Value: Cardinal);
  1798. begin
  1799. if (Value <> FDrawFrameBuffer) or (Value <> FReadFrameBuffer) or FInsideList then
  1800. begin
  1801. FDrawFrameBuffer := Value;
  1802. FReadFrameBuffer := Value;
  1803. gl.BindFramebuffer(GL_FRAMEBUFFER, Value);
  1804. end;
  1805. end;
  1806. procedure TGLStateCache.SetFrontFace(const Value: TGLFaceWinding);
  1807. begin
  1808. if (Value <> FFrontFace) or FInsideList then
  1809. begin
  1810. if FInsideList then
  1811. Include(FListStates[FCurrentList], sttPolygon)
  1812. else
  1813. FFrontFace := Value;
  1814. gl.FrontFace(cGLFaceWindingToGLEnum[Value]);
  1815. end;
  1816. end;
  1817. procedure TGLStateCache.SetGLAlphaFunction(func: TGLComparisonFunction; ref: Single);
  1818. {$IFDEF USE_CACHE_MISS_CHECK}
  1819. var
  1820. I: Cardinal;
  1821. E: Single;
  1822. {$ENDIF}
  1823. begin
  1824. { if FForwardContext then
  1825. exit; }
  1826. {$IFDEF USE_CACHE_MISS_CHECK}
  1827. gl.GetIntegerv(GL_ALPHA_TEST_FUNC, @I);
  1828. if cGLComparisonFunctionToGLEnum[FAlphaFunc] <> I then
  1829. GLSLogger.LogError(strStateCashMissing + 'AlphaTest function');
  1830. gl.GetFloatv(GL_ALPHA_TEST_REF, @E);
  1831. if FAlphaRef <> E then
  1832. GLSLogger.LogError(strStateCashMissing + 'AlphaTest reference');
  1833. {$ENDIF}
  1834. if (FAlphaFunc <> func) or (FAlphaRef <> ref) or FInsideList then
  1835. begin
  1836. if FInsideList then
  1837. Include(FListStates[FCurrentList], sttColorBuffer)
  1838. else
  1839. begin
  1840. FAlphaFunc := func;
  1841. FAlphaRef := ref;
  1842. end;
  1843. gl.AlphaFunc(cGLComparisonFunctionToGLEnum[func], ref);
  1844. end;
  1845. end;
  1846. function TGLStateCache.GetColorWriteMask(index: Integer): TGLColorMask;
  1847. begin
  1848. Result := FColorWriteMask[Index];
  1849. end;
  1850. function TGLStateCache.GetCurrentQuery(index: TGLQueryType): Cardinal;
  1851. begin
  1852. Result := FCurrentQuery[Index];
  1853. end;
  1854. function TGLStateCache.GetCurrentVertexAttrib(index: Integer): TGLVector;
  1855. begin
  1856. Result := FCurrentVertexAttrib[Index];
  1857. end;
  1858. function TGLStateCache.GetDepthRangeFar: TGLclampd;
  1859. begin
  1860. Result := FDepthRange[1];
  1861. end;
  1862. function TGLStateCache.GetDepthRangeNear: TGLclampd;
  1863. begin
  1864. Result := FDepthRange[0];
  1865. end;
  1866. function TGLStateCache.GetEnableBlend(index: Integer): TGLboolean;
  1867. begin
  1868. Result := FEnableBlend[Index];
  1869. end;
  1870. function TGLStateCache.GetEnableClipDistance(ClipDistance: Cardinal): TGLboolean;
  1871. begin
  1872. Result := FEnableClipDistance[ClipDistance];
  1873. end;
  1874. function TGLStateCache.GetSampleMaskValue(index: Integer): TGLbitfield;
  1875. begin
  1876. Result := FSampleMaskValue[Index];
  1877. end;
  1878. function TGLStateCache.GetMaxTextureSize: Cardinal;
  1879. begin
  1880. if FMaxTextureSize = 0 then
  1881. gl.GetIntegerv(GL_MAX_TEXTURE_SIZE, @FMaxTextureSize);
  1882. Result := FMaxTextureSize;
  1883. end;
  1884. function TGLStateCache.GetMaterialAmbient(const aFace: TGLCullFaceMode): TGLVector;
  1885. begin
  1886. Result := FFrontBackColors[ord(aFace)][1];
  1887. end;
  1888. function TGLStateCache.GetMaterialDiffuse(const aFace: TGLCullFaceMode): TGLVector;
  1889. begin
  1890. Result := FFrontBackColors[ord(aFace)][2];
  1891. end;
  1892. function TGLStateCache.GetMaterialEmission(const aFace: TGLCullFaceMode): TGLVector;
  1893. begin
  1894. Result := FFrontBackColors[ord(aFace)][0];
  1895. end;
  1896. function TGLStateCache.GetMaterialShininess(const aFace: TGLCullFaceMode): Integer;
  1897. begin
  1898. Result := FFrontBackShininess[ord(aFace)];
  1899. end;
  1900. function TGLStateCache.GetMaterialSpecular(const aFace: TGLCullFaceMode): TGLVector;
  1901. begin
  1902. Result := FFrontBackColors[ord(aFace)][3];
  1903. end;
  1904. function TGLStateCache.GetMax3DTextureSize: Cardinal;
  1905. begin
  1906. if FMax3DTextureSize = 0 then
  1907. gl.GetIntegerv(GL_MAX_3D_TEXTURE_SIZE, @FMax3DTextureSize);
  1908. Result := FMax3DTextureSize;
  1909. end;
  1910. function TGLStateCache.GetMaxCubeTextureSize: Cardinal;
  1911. begin
  1912. if FMaxCubeTextureSize = 0 then
  1913. gl.GetIntegerv(GL_MAX_CUBE_MAP_TEXTURE_SIZE, @FMaxCubeTextureSize);
  1914. Result := FMaxCubeTextureSize;
  1915. end;
  1916. function TGLStateCache.GetMaxArrayTextureSize: Cardinal;
  1917. begin
  1918. if FMaxArrayTextureSize = 0 then
  1919. gl.GetIntegerv(GL_MAX_ARRAY_TEXTURE_LAYERS, @FMaxArrayTextureSize);
  1920. Result := FMaxArrayTextureSize;
  1921. end;
  1922. function TGLStateCache.GetMaxTextureImageUnits: Cardinal;
  1923. begin
  1924. if FMaxTextureImageUnits = 0 then
  1925. gl.GetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS, @FMaxTextureImageUnits);
  1926. Result := FMaxTextureImageUnits;
  1927. end;
  1928. function TGLStateCache.GetMaxTextureAnisotropy: Cardinal;
  1929. begin
  1930. if (FMaxTextureAnisotropy = 0) and GL.EXT_texture_filter_anisotropic then
  1931. gl.GetIntegerv(GL_MAX_TEXTURE_MAX_ANISOTROPY_EXT, @FMaxTextureAnisotropy);
  1932. Result := FMaxTextureAnisotropy;
  1933. end;
  1934. function TGLStateCache.GetMaxSamples: Cardinal;
  1935. begin
  1936. if (FMaxSamples = 0) and GL.EXT_multisample then
  1937. gl.GetIntegerv(GL_MAX_SAMPLES, @FMaxSamples);
  1938. Result := FMaxSamples;
  1939. end;
  1940. function TGLStateCache.GetTextureBinding(index: Integer; target: TGLTextureTarget): Cardinal;
  1941. begin
  1942. Result := FTextureBinding[Index, target];
  1943. end;
  1944. function TGLStateCache.GetTextureBindingTime(index: Integer; target: TGLTextureTarget): Double;
  1945. begin
  1946. Result := FTextureBindingTime[Index, target];
  1947. end;
  1948. function TGLStateCache.GetSamplerBinding(index: Cardinal): Cardinal;
  1949. begin
  1950. Result := FSamplerBinding[Index];
  1951. end;
  1952. procedure TGLStateCache.SetSamplerBinding(index: Cardinal; const Value: Cardinal);
  1953. begin
  1954. if Index > High(FSamplerBinding) then
  1955. exit;
  1956. if (Value <> FSamplerBinding[Index]) or FInsideList then
  1957. begin
  1958. if FInsideList then
  1959. Include(FListStates[FCurrentList], sttTexture)
  1960. else
  1961. FSamplerBinding[Index] := Value;
  1962. gl.BindSampler(Index, Value);
  1963. end;
  1964. end;
  1965. procedure TGLStateCache.SetTextureMatrix(const matrix: TGLMatrix);
  1966. begin
  1967. { if FForwardContext then
  1968. exit; }
  1969. if FInsideList then
  1970. Include(FListStates[FCurrentList], sttTransform)
  1971. else
  1972. FTextureMatrixIsIdentity[ActiveTexture] := False;
  1973. gl.MatrixMode(GL_TEXTURE);
  1974. gl.LoadMatrixf(PGLFloat(@matrix.V[0].X));
  1975. gl.MatrixMode(GL_MODELVIEW);
  1976. end;
  1977. procedure TGLStateCache.ResetTextureMatrix;
  1978. begin
  1979. { if FForwardContext then
  1980. exit; }
  1981. gl.MatrixMode(GL_TEXTURE);
  1982. gl.LoadIdentity;
  1983. FTextureMatrixIsIdentity[ActiveTexture] := True;
  1984. gl.MatrixMode(GL_MODELVIEW);
  1985. end;
  1986. procedure TGLStateCache.ResetAllTextureMatrix;
  1987. var
  1988. I: Integer;
  1989. lastActiveTexture: Cardinal;
  1990. begin
  1991. { if FForwardContext then
  1992. exit; }
  1993. lastActiveTexture := ActiveTexture;
  1994. gl.MatrixMode(GL_TEXTURE);
  1995. for I := High(FTextureMatrixIsIdentity) downto 0 do
  1996. if not FTextureMatrixIsIdentity[I] then
  1997. begin
  1998. ActiveTexture := I;
  1999. gl.LoadIdentity;
  2000. FTextureMatrixIsIdentity[I] := True;
  2001. end;
  2002. gl.MatrixMode(GL_MODELVIEW);
  2003. ActiveTexture := lastActiveTexture;
  2004. end;
  2005. procedure TGLStateCache.SetLineSmoothHint(const Value: TGLHintType);
  2006. begin
  2007. if (Value <> FLineSmoothHint) or FInsideList then
  2008. begin
  2009. if FInsideList then
  2010. Include(FListStates[FCurrentList], sttHint)
  2011. else
  2012. FLineSmoothHint := Value;
  2013. gl.Hint(GL_LINE_SMOOTH_HINT, cGLHintToGLEnum[Value]);
  2014. end;
  2015. end;
  2016. procedure TGLStateCache.SetLineWidth(const Value: TGLfloat);
  2017. begin
  2018. // note: wide lines no longer deprecated (see OpenGL spec)
  2019. if (Value <> FLineWidth) or FInsideList then
  2020. begin
  2021. if FInsideList then
  2022. Include(FListStates[FCurrentList], sttLine)
  2023. else
  2024. FLineWidth := Value;
  2025. gl.LineWidth(Value);
  2026. end;
  2027. end;
  2028. procedure TGLStateCache.SetLineStippleFactor(const Value: TGLint);
  2029. begin
  2030. if (Value <> FLineStippleFactor) or FInsideList then
  2031. begin
  2032. if FInsideList then
  2033. Include(FListStates[FCurrentList], sttLine)
  2034. else
  2035. FLineStippleFactor := Value;
  2036. gl.LineStipple(Value, FLineStipplePattern);
  2037. end;
  2038. end;
  2039. procedure TGLStateCache.SetLineStipplePattern(const Value: TGLushort);
  2040. begin
  2041. if (Value <> FLineStipplePattern) or FInsideList then
  2042. begin
  2043. if FInsideList then
  2044. Include(FListStates[FCurrentList], sttLine)
  2045. else
  2046. FLineStipplePattern := Value;
  2047. gl.LineStipple(FLineStippleFactor, Value);
  2048. end;
  2049. end;
  2050. procedure TGLStateCache.SetLogicOpMode(const Value: TGLLogicOp);
  2051. begin
  2052. if (Value <> FLogicOpMode) or FInsideList then
  2053. begin
  2054. if FInsideList then
  2055. Include(FListStates[FCurrentList], sttColorBuffer)
  2056. else
  2057. FLogicOpMode := Value;
  2058. gl.LogicOp(cGLLogicOpToGLEnum[Value]);
  2059. end;
  2060. end;
  2061. procedure TGLStateCache.SetPackAlignment(const Value: Cardinal);
  2062. begin
  2063. if Value <> FPackAlignment then
  2064. begin
  2065. FPackAlignment := Value;
  2066. gl.PixelStoref(GL_PACK_ALIGNMENT, Value);
  2067. end;
  2068. end;
  2069. procedure TGLStateCache.SetPackImageHeight(const Value: Cardinal);
  2070. begin
  2071. if Value <> FPackImageHeight then
  2072. begin
  2073. FPackImageHeight := Value;
  2074. gl.PixelStoref(GL_PACK_IMAGE_HEIGHT, Value);
  2075. end;
  2076. end;
  2077. procedure TGLStateCache.SetPackLSBFirst(const Value: TGLboolean);
  2078. begin
  2079. if Value <> FPackLSBFirst then
  2080. begin
  2081. FPackLSBFirst := Value;
  2082. gl.PixelStorei(GL_PACK_LSB_FIRST, byte(Value));
  2083. end;
  2084. end;
  2085. procedure TGLStateCache.SetPackRowLength(const Value: Cardinal);
  2086. begin
  2087. if Value <> FPackRowLength then
  2088. begin
  2089. FPackRowLength := Value;
  2090. gl.PixelStoref(GL_PACK_ROW_LENGTH, Value);
  2091. end;
  2092. end;
  2093. procedure TGLStateCache.SetPackSkipImages(const Value: Cardinal);
  2094. begin
  2095. if Value <> FPackSkipImages then
  2096. begin
  2097. FPackSkipImages := Value;
  2098. gl.PixelStoref(GL_PACK_SKIP_IMAGES, Value);
  2099. end;
  2100. end;
  2101. procedure TGLStateCache.SetPackSkipPixels(const Value: Cardinal);
  2102. begin
  2103. if Value <> FPackSkipPixels then
  2104. begin
  2105. FPackSkipPixels := Value;
  2106. gl.PixelStoref(GL_PACK_SKIP_PIXELS, Value);
  2107. end;
  2108. end;
  2109. procedure TGLStateCache.SetPackSkipRows(const Value: Cardinal);
  2110. begin
  2111. if Value <> FPackSkipRows then
  2112. begin
  2113. FPackSkipRows := Value;
  2114. gl.PixelStoref(GL_PACK_SKIP_ROWS, Value);
  2115. end;
  2116. end;
  2117. procedure TGLStateCache.SetPackSwapBytes(const Value: TGLboolean);
  2118. begin
  2119. if Value <> FPackSwapBytes then
  2120. begin
  2121. FPackSwapBytes := Value;
  2122. gl.PixelStorei(GL_PACK_SWAP_BYTES, byte(Value));
  2123. end;
  2124. end;
  2125. procedure TGLStateCache.SetPixelPackBufferBinding(const Value: Cardinal);
  2126. begin
  2127. if Value <> FPixelPackBufferBinding then
  2128. begin
  2129. FPixelPackBufferBinding := Value;
  2130. gl.BindBuffer(GL_PIXEL_PACK_BUFFER, Value);
  2131. end;
  2132. end;
  2133. procedure TGLStateCache.SetPixelUnpackBufferBinding(const Value: Cardinal);
  2134. begin
  2135. if Value <> FPixelUnpackBufferBinding then
  2136. begin
  2137. FPixelUnpackBufferBinding := Value;
  2138. gl.BindBuffer(GL_PIXEL_UNPACK_BUFFER, Value);
  2139. end;
  2140. end;
  2141. procedure TGLStateCache.SetPointFadeThresholdSize(const Value: TGLfloat);
  2142. begin
  2143. if (Value <> FPointFadeThresholdSize) or FInsideList then
  2144. begin
  2145. if FInsideList then
  2146. Include(FListStates[FCurrentList], sttPoint)
  2147. else
  2148. FPointFadeThresholdSize := Value;
  2149. gl.PointParameterf(GL_POINT_FADE_THRESHOLD_SIZE, Value);
  2150. end;
  2151. end;
  2152. procedure TGLStateCache.SetPointSize(const Value: TGLfloat);
  2153. begin
  2154. if (Value <> FPointSize) or FInsideList then
  2155. begin
  2156. if FInsideList then
  2157. Include(FListStates[FCurrentList], sttPoint)
  2158. else
  2159. FPointSize := Value;
  2160. gl.PointSize(Value);
  2161. end;
  2162. end;
  2163. procedure TGLStateCache.SetPointSpriteCoordOrigin(const Value: Cardinal);
  2164. begin
  2165. if (Value <> FPointSpriteCoordOrigin) or FInsideList then
  2166. begin
  2167. if FInsideList then
  2168. Include(FListStates[FCurrentList], sttPoint)
  2169. else
  2170. FPointSpriteCoordOrigin := Value;
  2171. gl.PointParameterf(GL_POINT_SPRITE_COORD_ORIGIN, Value);
  2172. end;
  2173. end;
  2174. procedure TGLStateCache.SetPolygonMode(const Value: TGLPolygonMode);
  2175. begin
  2176. if (Value <> FPolygonMode) or FInsideList then
  2177. begin
  2178. if FInsideList then
  2179. Include(FListStates[FCurrentList], sttPolygon)
  2180. else
  2181. begin
  2182. FPolygonMode := Value;
  2183. FPolygonBackMode := Value;
  2184. end;
  2185. gl.PolygonMode(GL_FRONT_AND_BACK, cGLPolygonModeToGLEnum[Value]);
  2186. end;
  2187. end;
  2188. procedure TGLStateCache.SetPolygonOffset(const factor, units: TGLfloat);
  2189. begin
  2190. if (factor <> FPolygonOffsetFactor) or (units <> FPolygonOffsetUnits) or FInsideList then
  2191. begin
  2192. if FInsideList then
  2193. Include(FListStates[FCurrentList], sttPolygon)
  2194. else
  2195. begin
  2196. FPolygonOffsetFactor := factor;
  2197. FPolygonOffsetUnits := units;
  2198. end;
  2199. gl.PolygonOffset(factor, units);
  2200. end;
  2201. end;
  2202. procedure TGLStateCache.SetPolygonOffsetFactor(const Value: TGLfloat);
  2203. begin
  2204. if (Value <> FPolygonOffsetFactor) or FInsideList then
  2205. begin
  2206. if FInsideList then
  2207. Include(FListStates[FCurrentList], sttPolygon)
  2208. else
  2209. FPolygonOffsetFactor := Value;
  2210. gl.PolygonOffset(Value, FPolygonOffsetUnits);
  2211. end;
  2212. end;
  2213. procedure TGLStateCache.SetPolygonOffsetUnits(const Value: TGLfloat);
  2214. begin
  2215. if (Value <> FPolygonOffsetUnits) or FInsideList then
  2216. begin
  2217. if FInsideList then
  2218. Include(FListStates[FCurrentList], sttPolygon)
  2219. else
  2220. FPolygonOffsetUnits := Value;
  2221. gl.PolygonOffset(FPolygonOffsetFactor, Value);
  2222. end;
  2223. end;
  2224. procedure TGLStateCache.SetPolygonSmoothHint(const Value: TGLHintType);
  2225. begin
  2226. if (Value <> FPolygonSmoothHint) or FInsideList then
  2227. begin
  2228. if FInsideList then
  2229. Include(FListStates[FCurrentList], sttHint)
  2230. else
  2231. FPolygonSmoothHint := Value;
  2232. gl.Hint(GL_POLYGON_SMOOTH_HINT, cGLHintToGLEnum[Value]);
  2233. end;
  2234. end;
  2235. procedure TGLStateCache.SetProvokingVertex(const Value: Cardinal);
  2236. begin
  2237. if Value <> FProvokingVertex then
  2238. begin
  2239. FProvokingVertex := Value;
  2240. gl.ProvokingVertex(Value);
  2241. end;
  2242. end;
  2243. procedure TGLStateCache.SetReadFrameBuffer(const Value: Cardinal);
  2244. begin
  2245. if Value <> FReadFrameBuffer then
  2246. begin
  2247. FReadFrameBuffer := Value;
  2248. gl.BindFramebuffer(GL_READ_FRAMEBUFFER, Value);
  2249. end;
  2250. end;
  2251. procedure TGLStateCache.SetRenderBuffer(const Value: Cardinal);
  2252. begin
  2253. if Value <> FRenderBuffer then
  2254. begin
  2255. FRenderBuffer := Value;
  2256. gl.BindRenderbuffer(GL_RENDERBUFFER, Value);
  2257. end;
  2258. end;
  2259. procedure TGLStateCache.SetSampleCoverage(const Value: TGLfloat; invert: TGLboolean);
  2260. begin
  2261. if (Value <> FSampleCoverageValue) or (invert <> FSampleCoverageInvert) or FInsideList then
  2262. begin
  2263. if FInsideList then
  2264. Include(FListStates[FCurrentList], sttMultisample)
  2265. else
  2266. begin
  2267. FSampleCoverageValue := Value;
  2268. FSampleCoverageInvert := invert;
  2269. end;
  2270. gl.SampleCoverage(Value, invert);
  2271. end;
  2272. end;
  2273. procedure TGLStateCache.SetSampleCoverageInvert(const Value: TGLboolean);
  2274. begin
  2275. if (Value <> FSampleCoverageInvert) or FInsideList then
  2276. begin
  2277. if FInsideList then
  2278. Include(FListStates[FCurrentList], sttMultisample)
  2279. else
  2280. FSampleCoverageInvert := Value;
  2281. gl.SampleCoverage(FSampleCoverageValue, Value);
  2282. end;
  2283. end;
  2284. procedure TGLStateCache.SetSampleCoverageValue(const Value: TGLfloat);
  2285. begin
  2286. if (Value <> FSampleCoverageValue) or FInsideList then
  2287. begin
  2288. if FInsideList then
  2289. Include(FListStates[FCurrentList], sttMultisample)
  2290. else
  2291. FSampleCoverageValue := Value;
  2292. gl.SampleCoverage(Value, FSampleCoverageInvert);
  2293. end;
  2294. end;
  2295. procedure TGLStateCache.SetSampleMaskValue(index: Integer; const Value: TGLbitfield);
  2296. begin
  2297. if (FSampleMaskValue[Index] <> Value) or FInsideList then
  2298. begin
  2299. if FInsideList then
  2300. Include(FListStates[FCurrentList], sttMultisample)
  2301. else
  2302. FSampleMaskValue[Index] := Value;
  2303. gl.SampleMaski(Index, Value);
  2304. end;
  2305. end;
  2306. procedure TGLStateCache.SetScissorBox(const Value: TVector4i);
  2307. begin
  2308. if not VectorEquals(FScissorBox, Value) or FInsideList then
  2309. begin
  2310. if FInsideList then
  2311. Include(FListStates[FCurrentList], sttScissor)
  2312. else
  2313. FScissorBox := Value;
  2314. gl.Scissor(Value.X, Value.Y, Value.Z, Value.W);
  2315. end;
  2316. end;
  2317. procedure TGLStateCache.SetStencilBackWriteMask(const Value: Cardinal);
  2318. begin
  2319. if (Value <> FStencilBackWriteMask) or FInsideList then
  2320. begin
  2321. if FInsideList then
  2322. Include(FListStates[FCurrentList], sttStencilBuffer)
  2323. else
  2324. FStencilBackWriteMask := Value;
  2325. // DONE: ignore if unsupported
  2326. if gl.VERSION_2_0 then
  2327. gl.StencilMaskSeparate(GL_BACK, Value);
  2328. end;
  2329. end;
  2330. procedure TGLStateCache.SetStencilClearValue(const Value: Cardinal);
  2331. {$IFDEF USE_CACHE_MISS_CHECK}
  2332. var
  2333. I: Cardinal;
  2334. {$ENDIF}
  2335. begin
  2336. {$IFDEF USE_CACHE_MISS_CHECK}
  2337. gl.GetIntegerv(GL_STENCIL_CLEAR_VALUE, @I);
  2338. if FStencilClearValue <> I then
  2339. GLSLogger.LogError(strStateCashMissing + 'Stencil clear value');
  2340. {$ENDIF}
  2341. if (Value <> FStencilClearValue) or FInsideList then
  2342. begin
  2343. if FInsideList then
  2344. Include(FListStates[FCurrentList], sttStencilBuffer)
  2345. else
  2346. FStencilClearValue := Value;
  2347. gl.ClearStencil(Value);
  2348. end;
  2349. end;
  2350. procedure TGLStateCache.SetColorClearValue(const Value: TGLVector);
  2351. begin
  2352. if not VectorEquals(Value, FColorClearValue) or FInsideList then
  2353. begin
  2354. if FInsideList then
  2355. Include(FListStates[FCurrentList], sttColorBuffer)
  2356. else
  2357. FColorClearValue := Value;
  2358. gl.ClearColor(Value.X, Value.Y, Value.Z, Value.W);
  2359. end;
  2360. end;
  2361. procedure TGLStateCache.SetColorMask(mask: TGLColorMask);
  2362. var
  2363. I: Integer;
  2364. begin
  2365. // it might be faster to keep track of whether all draw buffers are same
  2366. // value or not, since using this is probably more common than setting
  2367. // the color write mask for individual draw buffers
  2368. if FInsideList then
  2369. Include(FListStates[FCurrentList], sttColorBuffer)
  2370. else
  2371. for I := low(FColorWriteMask) to high(FColorWriteMask) do
  2372. begin
  2373. FColorWriteMask[I] := mask;
  2374. end;
  2375. gl.ColorMask(ccRed in mask, ccGreen in mask, ccBlue in mask, ccAlpha in mask);
  2376. end;
  2377. procedure TGLStateCache.SetStencilFuncSeparate(const face: TGLCullFaceMode; const func: TGLStencilFunction; const ref: TGLint;
  2378. const mask: Cardinal);
  2379. {$IFDEF USE_CACHE_MISS_CHECK}
  2380. var
  2381. UI: Cardinal;
  2382. I: TGLint;
  2383. {$ENDIF}
  2384. begin
  2385. // if (func<>FStencilFunc) or (ref<>FStencilRef) or (mask<>FStencilValueMask)
  2386. // or FInsideList then
  2387. {$IFDEF USE_CACHE_MISS_CHECK}
  2388. gl.GetIntegerv(GL_STENCIL_FUNC, @UI);
  2389. if cGLComparisonFunctionToGLEnum[FStencilFunc] <> UI then
  2390. GLSLogger.LogError(strStateCashMissing + 'Stencil function');
  2391. gl.GetIntegerv(GL_STENCIL_REF, @I);
  2392. if FStencilRef <> I then
  2393. GLSLogger.LogError(strStateCashMissing + 'Stencil reference');
  2394. GLSLogger.LogError(strStateCashMissing + 'Stencil function');
  2395. gl.GetIntegerv(GL_STENCIL_VALUE_MASK, @UI);
  2396. if FStencilValueMask <> UI then
  2397. GLSLogger.LogError(strStateCashMissing + 'Stencil value mask');
  2398. {$ENDIF}
  2399. begin
  2400. if FInsideList then
  2401. Include(FListStates[FCurrentList], sttStencilBuffer)
  2402. else
  2403. case face of
  2404. cmFront:
  2405. begin
  2406. FStencilFunc := func;
  2407. FStencilRef := ref;
  2408. FStencilValueMask := mask;
  2409. end;
  2410. cmBack:
  2411. begin
  2412. FStencilBackFunc := func;
  2413. FStencilBackRef := ref;
  2414. FStencilBackValueMask := mask;
  2415. end;
  2416. cmFrontAndBack:
  2417. begin
  2418. FStencilFunc := func;
  2419. FStencilRef := ref;
  2420. FStencilValueMask := mask;
  2421. FStencilBackFunc := func;
  2422. FStencilBackRef := ref;
  2423. FStencilBackValueMask := mask;
  2424. end;
  2425. end;
  2426. gl.StencilFuncSeparate(cGLCullFaceModeToGLEnum[face], cGLComparisonFunctionToGLEnum[func], ref, mask);
  2427. end;
  2428. end;
  2429. procedure TGLStateCache.SetStencilFunc(const func: TGLStencilFunction; const ref: TGLint; const mask: Cardinal);
  2430. begin
  2431. if (func <> FStencilFunc) or (ref <> FStencilRef) or (mask <> FStencilValueMask) or FInsideList then
  2432. begin
  2433. if FInsideList then
  2434. Include(FListStates[FCurrentList], sttStencilBuffer)
  2435. else
  2436. begin
  2437. FStencilFunc := func;
  2438. FStencilRef := ref;
  2439. FStencilValueMask := mask;
  2440. end;
  2441. gl.StencilFunc(cGLComparisonFunctionToGLEnum[func], ref, mask);
  2442. end;
  2443. end;
  2444. procedure TGLStateCache.SetStencilOp(const fail, zfail, zpass: TGLStencilOp);
  2445. {$IFDEF USE_CACHE_MISS_CHECK}
  2446. var
  2447. I: Cardinal;
  2448. {$ENDIF}
  2449. begin
  2450. {$IFDEF USE_CACHE_MISS_CHECK}
  2451. gl.GetIntegerv(GL_STENCIL_FAIL, @I);
  2452. if cGLStencilOpToGLEnum[FStencilFail] <> I then
  2453. GLSLogger.LogError(strStateCashMissing + 'Stencil fail');
  2454. gl.GetIntegerv(GL_STENCIL_PASS_DEPTH_FAIL, @I);
  2455. if cGLStencilOpToGLEnum[FStencilPassDepthFail] <> I then
  2456. GLSLogger.LogError(strStateCashMissing + 'Stencil zfail');
  2457. gl.GetIntegerv(GL_STENCIL_PASS_DEPTH_PASS, @I);
  2458. if cGLStencilOpToGLEnum[FStencilPassDepthPass] <> I then
  2459. GLSLogger.LogError(strStateCashMissing + 'Stencil zpass');
  2460. {$ENDIF}
  2461. if (fail <> FStencilFail) or (zfail <> FStencilPassDepthFail) or (zpass <> FStencilPassDepthPass) or FInsideList then
  2462. begin
  2463. if FInsideList then
  2464. Include(FListStates[FCurrentList], sttStencilBuffer)
  2465. else
  2466. begin
  2467. FStencilFail := fail;
  2468. FStencilPassDepthFail := zfail;
  2469. FStencilPassDepthPass := zpass;
  2470. end;
  2471. gl.StencilOp(cGLStencilOpToGLEnum[fail],
  2472. cGLStencilOpToGLEnum[zfail],
  2473. cGLStencilOpToGLEnum[zpass]);
  2474. end;
  2475. end;
  2476. procedure TGLStateCache.SetStencilOpSeparate(const face: TGLCullFaceMode; const sfail, dpfail, dppass: TGLStencilOp);
  2477. begin
  2478. if FInsideList then
  2479. Include(FListStates[FCurrentList], sttStencilBuffer)
  2480. else
  2481. case face of
  2482. cmFront:
  2483. begin
  2484. FStencilFail := sfail;
  2485. FStencilPassDepthFail := dpfail;
  2486. FStencilPassDepthPass := dppass;
  2487. end;
  2488. cmBack:
  2489. begin
  2490. FStencilBackFail := sfail;
  2491. FStencilBackPassDepthFail := dpfail;
  2492. FStencilBackPassDepthPass := dppass;
  2493. end;
  2494. cmFrontAndBack:
  2495. begin
  2496. FStencilFail := sfail;
  2497. FStencilPassDepthFail := dpfail;
  2498. FStencilPassDepthPass := dppass;
  2499. FStencilBackFail := sfail;
  2500. FStencilBackPassDepthFail := dpfail;
  2501. FStencilBackPassDepthPass := dppass;
  2502. end;
  2503. end;
  2504. gl.StencilOpSeparate(cGLCullFaceModeToGLEnum[face], cGLStencilOpToGLEnum[sfail], cGLStencilOpToGLEnum[dpfail],
  2505. cGLStencilOpToGLEnum[dppass]);
  2506. end;
  2507. procedure TGLStateCache.SetStencilWriteMask(const Value: Cardinal);
  2508. {$IFDEF USE_CACHE_MISS_CHECK}
  2509. var
  2510. I: Cardinal;
  2511. {$ENDIF}
  2512. begin
  2513. {$IFDEF USE_CACHE_MISS_CHECK}
  2514. gl.GetIntegerv(GL_STENCIL_WRITEMASK, @I);
  2515. if FStencilWriteMask <> I then
  2516. GLSLogger.LogError(strStateCashMissing + 'Stencil write mask');
  2517. {$ENDIF}
  2518. if (Value <> FStencilWriteMask) or FInsideList then
  2519. begin
  2520. if FInsideList then
  2521. Include(FListStates[FCurrentList], sttStencilBuffer)
  2522. else
  2523. FStencilWriteMask := Value;
  2524. gl.StencilMaskSeparate(GL_FRONT, Value);
  2525. end;
  2526. end;
  2527. procedure TGLStateCache.SetTextureBinding(index: Integer; target: TGLTextureTarget; const Value: Cardinal);
  2528. var
  2529. lastActiveTexture: Cardinal;
  2530. begin
  2531. if target = ttNoShape then
  2532. exit;
  2533. if (Value <> FTextureBinding[Index, target]) or FInsideList then
  2534. begin
  2535. if FInsideList then
  2536. Include(FListStates[FCurrentList], sttTexture)
  2537. else
  2538. FTextureBinding[Index, target] := Value;
  2539. lastActiveTexture := ActiveTexture;
  2540. ActiveTexture := Index;
  2541. gl.BindTexture(cGLTexTypeToGLEnum[target], Value);
  2542. ActiveTexture := lastActiveTexture;
  2543. end;
  2544. FTextureBindingTime[Index, target] := AppTime;
  2545. end;
  2546. function TGLStateCache.GetActiveTextureEnabled(target: TGLTextureTarget): Boolean;
  2547. begin
  2548. Result := FActiveTextureEnabling[FActiveTexture][target];
  2549. end;
  2550. procedure TGLStateCache.SetActiveTextureEnabled(target: TGLTextureTarget; const Value: Boolean);
  2551. var
  2552. glTarget: Cardinal;
  2553. begin
  2554. glTarget := DecodeTextureTarget(target);
  2555. if { FForwardContext or } not IsTargetSupported(glTarget) then
  2556. exit;
  2557. if (Value <> FActiveTextureEnabling[FActiveTexture][target]) or FInsideList then
  2558. begin
  2559. if FInsideList then
  2560. Include(FListStates[FCurrentList], sttEnable)
  2561. else
  2562. FActiveTextureEnabling[FActiveTexture][target] := Value;
  2563. if Value then
  2564. gl.Enable(glTarget)
  2565. else
  2566. gl.Disable(glTarget);
  2567. end;
  2568. end;
  2569. procedure TGLStateCache.SetTextureCompressionHint(const Value: TGLHintType);
  2570. begin
  2571. if (Value <> FTextureCompressionHint) or FInsideList then
  2572. begin
  2573. if FInsideList then
  2574. Include(FListStates[FCurrentList], sttHint)
  2575. else
  2576. FTextureCompressionHint := Value;
  2577. gl.Hint(GL_TEXTURE_COMPRESSION_HINT, cGLHintToGLEnum[Value]);
  2578. end;
  2579. end;
  2580. procedure TGLStateCache.SetTransformFeedbackBufferBinding(const Value: Cardinal);
  2581. begin
  2582. if (Value <> FTransformFeedbackBufferBinding) or FInsideList then
  2583. begin
  2584. FTransformFeedbackBufferBinding := Value;
  2585. gl.BindBuffer(GL_TRANSFORM_FEEDBACK_BUFFER, Value);
  2586. end;
  2587. end;
  2588. procedure TGLStateCache.SetEnableTextureCubeMapSeamless(const Value: TGLboolean);
  2589. begin
  2590. if Value <> FEnableTextureCubeMapSeamless then
  2591. begin
  2592. FEnableTextureCubeMapSeamless := Value;
  2593. if Value = True then
  2594. gl.Enable(GL_TEXTURE_CUBE_MAP_SEAMLESS)
  2595. else
  2596. gl.Disable(GL_TEXTURE_CUBE_MAP_SEAMLESS);
  2597. end;
  2598. end;
  2599. procedure TGLStateCache.NewList(list: Cardinal; mode: Cardinal);
  2600. var
  2601. I: Cardinal;
  2602. begin
  2603. Assert(mode = GL_COMPILE, 'Compile & executing not supported by TGLStateCache');
  2604. FCurrentList := list - 1;
  2605. // while High(FListStates) < Integer(FCurrentList) do
  2606. // SetLength(FListStates, 2 * Length(FListStates));
  2607. FListStates[FCurrentList] := [];
  2608. FInsideList := True;
  2609. // Reset VBO binding and client attribute
  2610. begin
  2611. if GL.ARB_vertex_buffer_object then
  2612. begin
  2613. ArrayBufferBinding := 0;
  2614. ElementBufferBinding := 0;
  2615. for I := 0 to 15 do
  2616. gl.DisableVertexAttribArray(I);
  2617. end;
  2618. gl.NewList(list, mode);
  2619. end;
  2620. end;
  2621. procedure TGLStateCache.EndList;
  2622. begin
  2623. gl.EndList;
  2624. FInsideList := False;
  2625. end;
  2626. procedure TGLStateCache.CallList(list: Cardinal);
  2627. begin
  2628. // while High(FListStates) < Integer(list) do
  2629. // SetLength(FListStates, 2 * Length(FListStates));
  2630. if FListStates[list - 1] <> [] then
  2631. begin
  2632. PushAttrib(FListStates[list - 1]);
  2633. gl.CallList(list);
  2634. PopAttrib;
  2635. end
  2636. else
  2637. gl.CallList(list);
  2638. end;
  2639. procedure TGLStateCache.SetUniformBufferBinding(const Value: Cardinal);
  2640. begin
  2641. Assert(not FInsideList);
  2642. if Value <> FUniformBufferBinding then
  2643. begin
  2644. FUniformBufferBinding := Value;
  2645. gl.BindBuffer(GL_UNIFORM_BUFFER, Value);
  2646. end;
  2647. end;
  2648. procedure TGLStateCache.SetBufferIndexedBinding(const Value: Cardinal;
  2649. ATarget: TGLBufferBindingTarget; AIndex: Cardinal; ABufferSize: TGLsizeiptr);
  2650. begin
  2651. Assert(not FInsideList);
  2652. if (FUBOStates[ATarget, AIndex].FUniformBufferBinding <> Value)
  2653. or (FUBOStates[ATarget, AIndex].FOffset > 0)
  2654. or (FUBOStates[ATarget, AIndex].FSize <> ABufferSize) then
  2655. begin
  2656. case ATarget of
  2657. bbtUniform:
  2658. FUniformBufferBinding := Value;
  2659. bbtTransformFeedBack:
  2660. FTransformFeedbackBufferBinding := Value;
  2661. end;
  2662. FUBOStates[ATarget, AIndex].FUniformBufferBinding := Value;
  2663. FUBOStates[ATarget, AIndex].FOffset := 0;
  2664. FUBOStates[ATarget, AIndex].FSize := ABufferSize;
  2665. gl.BindBufferBase(cGLBufferBindingTarget[ATarget], AIndex, Value);
  2666. end
  2667. else
  2668. case ATarget of
  2669. bbtUniform: SetUniformBufferBinding(Value);
  2670. bbtTransformFeedBack: SetTransformFeedbackBufferBinding(Value);
  2671. end;
  2672. end;
  2673. procedure TGLStateCache.SetBufferIndexedBinding(const Value: Cardinal; ATarget: TGLBufferBindingTarget; AIndex: Cardinal;
  2674. AOffset: TGLintptr; ARangeSize: TGLsizeiptr);
  2675. begin
  2676. Assert(not FInsideList);
  2677. if (FUBOStates[ATarget, AIndex].FUniformBufferBinding <> Value)
  2678. or (FUBOStates[ATarget, AIndex].FOffset <> AOffset)
  2679. or (FUBOStates[ATarget, AIndex].FSize <> ARangeSize) then
  2680. begin
  2681. case ATarget of
  2682. bbtUniform: FUniformBufferBinding := Value;
  2683. bbtTransformFeedBack: FTransformFeedbackBufferBinding := Value;
  2684. end;
  2685. FUBOStates[ATarget, AIndex].FUniformBufferBinding := Value;
  2686. FUBOStates[ATarget, AIndex].FOffset := AOffset;
  2687. FUBOStates[ATarget, AIndex].FSize := ARangeSize;
  2688. gl.BindBufferRange(cGLBufferBindingTarget[ATarget], AIndex, Value, AOffset, ARangeSize);
  2689. end;
  2690. end;
  2691. function TGLStateCache.GetMaxTextureUnits: Cardinal;
  2692. begin
  2693. if FMaxTextureUnits = 0 then
  2694. gl.GetIntegerv(GL_MAX_TEXTURE_IMAGE_UNITS_ARB, @FMaxTextureUnits);
  2695. Result := FMaxTextureUnits;
  2696. end;
  2697. procedure TGLStateCache.SetUnpackAlignment(const Value: Cardinal);
  2698. begin
  2699. if Value <> FUnpackAlignment then
  2700. begin
  2701. FUnpackAlignment := Value;
  2702. gl.PixelStoref(GL_UNPACK_ALIGNMENT, Value);
  2703. end;
  2704. end;
  2705. procedure TGLStateCache.SetUnpackImageHeight(const Value: Cardinal);
  2706. begin
  2707. if Value <> FUnpackImageHeight then
  2708. begin
  2709. FUnpackImageHeight := Value;
  2710. gl.PixelStoref(GL_UNPACK_IMAGE_HEIGHT, Value);
  2711. end;
  2712. end;
  2713. procedure TGLStateCache.SetUnpackLSBFirst(const Value: TGLboolean);
  2714. begin
  2715. if Value <> FUnpackLSBFirst then
  2716. begin
  2717. FUnpackLSBFirst := Value;
  2718. gl.PixelStorei(GL_UNPACK_LSB_FIRST, byte(Value));
  2719. end;
  2720. end;
  2721. procedure TGLStateCache.SetUnpackRowLength(const Value: Cardinal);
  2722. begin
  2723. if Value <> FUnpackRowLength then
  2724. begin
  2725. FUnpackRowLength := Value;
  2726. gl.PixelStoref(GL_UNPACK_ROW_LENGTH, Value);
  2727. end;
  2728. end;
  2729. procedure TGLStateCache.SetUnpackSkipImages(const Value: Cardinal);
  2730. begin
  2731. if Value <> FUnpackSkipImages then
  2732. begin
  2733. FUnpackSkipImages := Value;
  2734. gl.PixelStoref(GL_UNPACK_SKIP_IMAGES, Value);
  2735. end;
  2736. end;
  2737. procedure TGLStateCache.SetUnpackSkipPixels(const Value: Cardinal);
  2738. begin
  2739. if Value <> FUnpackSkipPixels then
  2740. begin
  2741. FUnpackSkipPixels := Value;
  2742. gl.PixelStoref(GL_UNPACK_SKIP_PIXELS, Value);
  2743. end;
  2744. end;
  2745. procedure TGLStateCache.SetUnpackSkipRows(const Value: Cardinal);
  2746. begin
  2747. if Value <> FUnpackSkipRows then
  2748. begin
  2749. FUnpackSkipRows := Value;
  2750. gl.PixelStoref(GL_UNPACK_SKIP_ROWS, Value);
  2751. end;
  2752. end;
  2753. procedure TGLStateCache.SetUnpackSwapBytes(const Value: TGLboolean);
  2754. begin
  2755. if Value <> FUnpackSwapBytes then
  2756. begin
  2757. FUnpackSwapBytes := Value;
  2758. gl.PixelStorei(GL_UNPACK_SWAP_BYTES, byte(Value));
  2759. end;
  2760. end;
  2761. procedure TGLStateCache.SetViewPort(const Value: TVector4i);
  2762. begin
  2763. if not VectorEquals(Value, FViewPort) or FInsideList then
  2764. begin
  2765. if FInsideList then
  2766. Include(FListStates[FCurrentList], sttViewport)
  2767. else
  2768. FViewPort := Value;
  2769. gl.ViewPort(Value.X, Value.Y, Value.Z, Value.W);
  2770. end;
  2771. end;
  2772. procedure TGLStateCache.SetFFPLight(Value: Boolean);
  2773. begin
  2774. FFFPLight := Value { and not FForwardContext };
  2775. end;
  2776. function TGLStateCache.GetMaxLights: Integer;
  2777. begin
  2778. if FMaxLights = 0 then
  2779. { if FForwardContext then
  2780. FMaxLights := MAX_HARDWARE_LIGHT
  2781. else }
  2782. gl.GetIntegerv(GL_MAX_LIGHTS, @FMaxLights);
  2783. Result := FMaxLights;
  2784. end;
  2785. function TGLStateCache.GetLightEnabling(I: Integer): Boolean;
  2786. begin
  2787. Result := FLightEnabling[I];
  2788. end;
  2789. procedure TGLStateCache.SetLightEnabling(I: Integer; Value: Boolean);
  2790. var
  2791. J, K: Integer;
  2792. begin
  2793. if (FLightEnabling[I] <> Value) or FInsideList then
  2794. begin
  2795. if FInsideList then
  2796. Include(FListStates[FCurrentList], sttLighting)
  2797. else
  2798. FLightEnabling[I] := Value;
  2799. if FFFPLight then
  2800. begin
  2801. if Value then
  2802. gl.Enable(GL_LIGHT0 + I)
  2803. else
  2804. gl.Disable(GL_LIGHT0 + I);
  2805. end;
  2806. K := 0;
  2807. for J := 0 to MAX_HARDWARE_LIGHT - 1 do
  2808. if FLightEnabling[J] then
  2809. begin
  2810. FLightIndices[K] := J;
  2811. Inc(K);
  2812. end;
  2813. FLightNumber := K;
  2814. FShaderLightStatesChanged := True;
  2815. if Assigned(FOnLightsChanged) then
  2816. FOnLightsChanged(Self);
  2817. end;
  2818. end;
  2819. function TGLStateCache.GetLightIndicesAsAddress: PGLInt;
  2820. begin
  2821. Result := @FLightIndices[0];
  2822. end;
  2823. function TGLStateCache.GetLightStateAsAddress: Pointer;
  2824. var
  2825. I, J, C: Integer;
  2826. begin
  2827. C := MinInteger(FLightNumber, MAX_SHADER_LIGHT);
  2828. if FShaderLightStatesChanged then
  2829. begin
  2830. if C > 0 then
  2831. begin
  2832. if GL.VERSION_3_0 then
  2833. begin
  2834. Move(FLightStates.Position,
  2835. FShaderLightStates.Position,
  2836. SizeOf(FShaderLightStates.Position));
  2837. Move(FLightStates.Ambient,
  2838. FShaderLightStates.Ambient,
  2839. SizeOf(FShaderLightStates.Ambient));
  2840. Move(FLightStates.Diffuse,
  2841. FShaderLightStates.Diffuse,
  2842. SizeOf(FShaderLightStates.Diffuse));
  2843. Move(FLightStates.Specular,
  2844. FShaderLightStates.Specular,
  2845. SizeOf(FShaderLightStates.Specular));
  2846. Move(FLightStates.SpotDirection,
  2847. FShaderLightStates.SpotDirection,
  2848. SizeOf(FShaderLightStates.SpotDirection));
  2849. Move(FLightStates.SpotCosCutoffExponent,
  2850. FShaderLightStates.SpotCosCutoffExponent,
  2851. SizeOf(FShaderLightStates.SpotCosCutoffExponent));
  2852. Move(FLightStates.Attenuation,
  2853. FShaderLightStates.Attenuation,
  2854. SizeOf(FShaderLightStates.Attenuation));
  2855. end
  2856. else
  2857. begin
  2858. for I := C - 1 downto 0 do
  2859. begin
  2860. J := FLightIndices[I];
  2861. FShaderLightStates.Position[I] := FLightStates.Position[J];
  2862. FShaderLightStates.Ambient[I] := FLightStates.Ambient[J];
  2863. FShaderLightStates.Diffuse[I] := FLightStates.Diffuse[J];
  2864. FShaderLightStates.Specular[I] := FLightStates.Specular[J];
  2865. FShaderLightStates.SpotDirection[I] := FLightStates.SpotDirection[J];
  2866. FShaderLightStates.SpotCosCutoffExponent[I] := FLightStates.SpotCosCutoffExponent[J];
  2867. FShaderLightStates.Attenuation[I] := FLightStates.Attenuation[J];
  2868. end;
  2869. end;
  2870. end
  2871. else
  2872. FillChar(FShaderLightStatesChanged, SizeOf(FShaderLightStatesChanged), $00);
  2873. FShaderLightStatesChanged := False;
  2874. end;
  2875. Result := @FShaderLightStates;
  2876. end;
  2877. function TGLStateCache.GetLightPosition(I: Integer): TGLVector;
  2878. begin
  2879. Result := FLightStates.Position[I];
  2880. end;
  2881. procedure TGLStateCache.SetLightPosition(I: Integer; const Value: TGLVector);
  2882. begin
  2883. if not VectorEquals(Value, FLightStates.Position[I]) then
  2884. begin
  2885. FLightStates.Position[I] := Value;
  2886. FShaderLightStatesChanged := True;
  2887. if Assigned(FOnLightsChanged) then
  2888. FOnLightsChanged(Self);
  2889. end;
  2890. end;
  2891. function TGLStateCache.GetLightSpotDirection(I: Integer): TAffineVector;
  2892. begin
  2893. Result := AffineVectorMake(FLightStates.SpotDirection[I]);
  2894. end;
  2895. procedure TGLStateCache.SetLightSpotDirection(I: Integer; const Value: TAffineVector);
  2896. begin
  2897. if not VectorEquals(Value, AffineVectorMake(FLightStates.SpotDirection[I])) then
  2898. begin
  2899. FLightStates.SpotDirection[I] := VectorMake(Value);
  2900. FShaderLightStatesChanged := True;
  2901. if Assigned(FOnLightsChanged) then
  2902. FOnLightsChanged(Self);
  2903. end;
  2904. end;
  2905. function TGLStateCache.GetLightAmbient(I: Integer): TGLVector;
  2906. begin
  2907. Result := FLightStates.Ambient[I];
  2908. end;
  2909. procedure TGLStateCache.SetLightAmbient(I: Integer; const Value: TGLVector);
  2910. begin
  2911. if not VectorEquals(Value, FLightStates.Ambient[I]) or FInsideList then
  2912. begin
  2913. if FInsideList then
  2914. Include(FListStates[FCurrentList], sttLighting)
  2915. else
  2916. FLightStates.Ambient[I] := Value;
  2917. if FFFPLight then
  2918. gl.Lightfv(GL_LIGHT0 + I, GL_AMBIENT, @Value);
  2919. FShaderLightStatesChanged := True;
  2920. if Assigned(FOnLightsChanged) then
  2921. FOnLightsChanged(Self);
  2922. end;
  2923. end;
  2924. function TGLStateCache.GetLightDiffuse(I: Integer): TGLVector;
  2925. begin
  2926. Result := FLightStates.Diffuse[I];
  2927. end;
  2928. procedure TGLStateCache.SetLightDiffuse(I: Integer; const Value: TGLVector);
  2929. begin
  2930. if not VectorEquals(Value, FLightStates.Diffuse[I]) or FInsideList then
  2931. begin
  2932. if FInsideList then
  2933. Include(FListStates[FCurrentList], sttLighting)
  2934. else
  2935. FLightStates.Diffuse[I] := Value;
  2936. if FFFPLight then
  2937. gl.Lightfv(GL_LIGHT0 + I, GL_DIFFUSE, @Value);
  2938. FShaderLightStatesChanged := True;
  2939. if Assigned(FOnLightsChanged) then
  2940. FOnLightsChanged(Self);
  2941. end;
  2942. end;
  2943. function TGLStateCache.GetLightSpecular(I: Integer): TGLVector;
  2944. begin
  2945. Result := FLightStates.Specular[I];
  2946. end;
  2947. procedure TGLStateCache.SetLightSpecular(I: Integer; const Value: TGLVector);
  2948. begin
  2949. if not VectorEquals(Value, FLightStates.Specular[I]) or FInsideList then
  2950. begin
  2951. if FInsideList then
  2952. Include(FListStates[FCurrentList], sttLighting)
  2953. else
  2954. FLightStates.Specular[I] := Value;
  2955. if FFFPLight then
  2956. gl.Lightfv(GL_LIGHT0 + I, GL_SPECULAR, @Value);
  2957. FShaderLightStatesChanged := True;
  2958. if Assigned(FOnLightsChanged) then
  2959. FOnLightsChanged(Self);
  2960. end;
  2961. end;
  2962. function TGLStateCache.GetSpotCutoff(I: Integer): Single;
  2963. begin
  2964. Result := FSpotCutoff[I];
  2965. end;
  2966. procedure TGLStateCache.SetSpotCutoff(I: Integer; const Value: Single);
  2967. begin
  2968. if (Value <> FSpotCutoff[I]) or FInsideList then
  2969. begin
  2970. if FInsideList then
  2971. Include(FListStates[FCurrentList], sttLighting)
  2972. else
  2973. begin
  2974. FSpotCutoff[I] := Value;
  2975. FLightStates.SpotCosCutoffExponent[I].X := cos(DegToRadian(Value));
  2976. end;
  2977. if FFFPLight then
  2978. gl.Lightfv(GL_LIGHT0 + I, GL_SPOT_CUTOFF, @Value);
  2979. FShaderLightStatesChanged := True;
  2980. if Assigned(FOnLightsChanged) then
  2981. FOnLightsChanged(Self);
  2982. end;
  2983. end;
  2984. function TGLStateCache.GetSpotExponent(I: Integer): Single;
  2985. begin
  2986. Result := FLightStates.SpotCosCutoffExponent[I].Y;
  2987. end;
  2988. procedure TGLStateCache.SetSpotExponent(I: Integer; const Value: Single);
  2989. begin
  2990. if (Value <> FLightStates.SpotCosCutoffExponent[I].Y) or FInsideList then
  2991. begin
  2992. if FInsideList then
  2993. Include(FListStates[FCurrentList], sttLighting)
  2994. else
  2995. FLightStates.SpotCosCutoffExponent[I].Y := Value;
  2996. if FFFPLight then
  2997. gl.Lightfv(GL_LIGHT0 + I, GL_SPOT_EXPONENT, @Value);
  2998. FShaderLightStatesChanged := True;
  2999. if Assigned(FOnLightsChanged) then
  3000. FOnLightsChanged(Self);
  3001. end;
  3002. end;
  3003. function TGLStateCache.GetConstantAtten(I: Integer): Single;
  3004. begin
  3005. Result := FLightStates.Attenuation[I].X;
  3006. end;
  3007. procedure TGLStateCache.SetConstantAtten(I: Integer; const Value: Single);
  3008. begin
  3009. if (Value <> FLightStates.Attenuation[I].X) or FInsideList then
  3010. begin
  3011. if FInsideList then
  3012. Include(FListStates[FCurrentList], sttLighting)
  3013. else
  3014. FLightStates.Attenuation[I].X := Value;
  3015. if FFFPLight then
  3016. gl.Lightfv(GL_LIGHT0 + I, GL_CONSTANT_ATTENUATION, @Value);
  3017. FShaderLightStatesChanged := True;
  3018. if Assigned(FOnLightsChanged) then
  3019. FOnLightsChanged(Self);
  3020. end;
  3021. end;
  3022. function TGLStateCache.GetLinearAtten(I: Integer): Single;
  3023. begin
  3024. Result := FLightStates.Attenuation[I].Y;
  3025. end;
  3026. procedure TGLStateCache.SetLinearAtten(I: Integer; const Value: Single);
  3027. begin
  3028. if (Value <> FLightStates.Attenuation[I].Y) or FInsideList then
  3029. begin
  3030. if FInsideList then
  3031. Include(FListStates[FCurrentList], sttLighting)
  3032. else
  3033. FLightStates.Attenuation[I].Y := Value;
  3034. if FFFPLight then
  3035. gl.Lightfv(GL_LIGHT0 + I, GL_LINEAR_ATTENUATION, @Value);
  3036. FShaderLightStatesChanged := True;
  3037. if Assigned(FOnLightsChanged) then
  3038. FOnLightsChanged(Self);
  3039. end;
  3040. end;
  3041. function TGLStateCache.GetQuadAtten(I: Integer): Single;
  3042. begin
  3043. Result := FLightStates.Attenuation[I].Z;
  3044. end;
  3045. procedure TGLStateCache.SetQuadAtten(I: Integer; const Value: Single);
  3046. begin
  3047. if (Value <> FLightStates.Attenuation[I].Z) or FInsideList then
  3048. begin
  3049. if FInsideList then
  3050. Include(FListStates[FCurrentList], sttLighting)
  3051. else
  3052. FLightStates.Attenuation[I].Z := Value;
  3053. if FFFPLight then
  3054. gl.Lightfv(GL_LIGHT0 + I, GL_QUADRATIC_ATTENUATION, @Value);
  3055. FShaderLightStatesChanged := True;
  3056. if Assigned(FOnLightsChanged) then
  3057. FOnLightsChanged(Self);
  3058. end;
  3059. end;
  3060. procedure TGLStateCache.SetForwardContext(Value: Boolean);
  3061. begin
  3062. { if Value <> FForwardContext then
  3063. begin
  3064. FForwardContext := Value;
  3065. if Value then
  3066. begin
  3067. SetFFPlight(False);
  3068. end;
  3069. end;
  3070. }
  3071. end;
  3072. procedure TGLStateCache.SetColorWriting(flag: Boolean);
  3073. begin
  3074. if (FColorWriting <> flag) or FInsideList then
  3075. begin
  3076. if FInsideList then
  3077. Include(FListStates[FCurrentList], sttColorBuffer)
  3078. else
  3079. FColorWriting := flag;
  3080. gl.ColorMask(flag, flag, flag, flag);
  3081. end;
  3082. end;
  3083. procedure TGLStateCache.InvertFrontFace;
  3084. begin
  3085. if FFrontFace = fwCounterClockWise then
  3086. FrontFace := fwClockWise
  3087. else
  3088. FrontFace := fwCounterClockWise;
  3089. end;
  3090. procedure TGLStateCache.SetGLState(const aState: TGLState);
  3091. begin
  3092. Enable(aState);
  3093. end;
  3094. procedure TGLStateCache.UnSetGLState(const aState: TGLState);
  3095. begin
  3096. Disable(aState);
  3097. end;
  3098. procedure TGLStateCache.ResetGLPolygonMode;
  3099. begin
  3100. gl.PolygonMode(GL_FRONT_AND_BACK, GL_FILL);
  3101. FPolygonMode := pmFill;
  3102. FPolygonBackMode := pmFill;
  3103. end;
  3104. procedure TGLStateCache.ResetGLMaterialColors;
  3105. begin
  3106. gl.Materialfv(GL_FRONT_AND_BACK, GL_AMBIENT, @clrGray20);
  3107. gl.Materialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, @clrGray80);
  3108. gl.Materialfv(GL_FRONT_AND_BACK, GL_SPECULAR, @clrBlack);
  3109. gl.Materialfv(GL_FRONT_AND_BACK, GL_EMISSION, @clrBlack);
  3110. gl.Materiali(GL_FRONT_AND_BACK, GL_SHININESS, 0);
  3111. FillChar(FFrontBackColors, SizeOf(FFrontBackColors), 127);
  3112. FFrontBackShininess[0] := 0;
  3113. FFrontBackShininess[1] := 0;
  3114. end;
  3115. procedure TGLStateCache.ResetGLTexture(const TextureUnit: Integer);
  3116. var
  3117. t: TGLTextureTarget;
  3118. glTarget: Cardinal;
  3119. begin
  3120. gl.ActiveTexture(GL_TEXTURE0 + TextureUnit);
  3121. for t := Low(TGLTextureTarget) to High(TGLTextureTarget) do
  3122. begin
  3123. glTarget := DecodeTextureTarget(t);
  3124. if IsTargetSupported(glTarget) then
  3125. begin
  3126. gl.BindTexture(glTarget, 0);
  3127. FTextureBinding[TextureUnit, t] := 0;
  3128. end;
  3129. end;
  3130. gl.ActiveTexture(GL_TEXTURE0);
  3131. FActiveTexture := 0;
  3132. end;
  3133. procedure TGLStateCache.ResetGLCurrentTexture;
  3134. var
  3135. a: TGLint;
  3136. t: TGLTextureTarget;
  3137. glTarget: Cardinal;
  3138. begin
  3139. if GL.ARB_multitexture then
  3140. begin
  3141. for a := MaxTextureImageUnits - 1 to 0 do
  3142. begin
  3143. gl.ActiveTexture(GL_TEXTURE0 + a);
  3144. for t := Low(TGLTextureTarget) to High(TGLTextureTarget) do
  3145. begin
  3146. glTarget := DecodeTextureTarget(t);
  3147. if IsTargetSupported(glTarget) then
  3148. begin
  3149. gl.BindTexture(glTarget, 0);
  3150. FTextureBinding[a, t] := 0;
  3151. end;
  3152. end;
  3153. end;
  3154. end
  3155. else
  3156. for t := Low(TGLTextureTarget) to High(TGLTextureTarget) do
  3157. begin
  3158. glTarget := DecodeTextureTarget(t);
  3159. if IsTargetSupported(glTarget) then
  3160. begin
  3161. gl.BindTexture(glTarget, 0);
  3162. FTextureBinding[0, t] := 0;
  3163. end;
  3164. end;
  3165. end;
  3166. procedure TGLStateCache.ResetGLFrontFace;
  3167. begin
  3168. gl.FrontFace(GL_CCW);
  3169. FFrontFace := fwCounterClockWise;
  3170. end;
  3171. procedure TGLStateCache.SetGLFrontFaceCW;
  3172. begin
  3173. if FFrontFace = fwCounterClockWise then
  3174. begin
  3175. gl.FrontFace(GL_CW);
  3176. FFrontFace := fwClockWise;
  3177. end;
  3178. end;
  3179. procedure TGLStateCache.ResetAll;
  3180. begin
  3181. {$WARN SYMBOL_DEPRECATED OFF}
  3182. ResetGLPolygonMode;
  3183. ResetGLMaterialColors;
  3184. ResetGLCurrentTexture;
  3185. ResetGLFrontFace;
  3186. {$WARN SYMBOL_DEPRECATED ON}
  3187. end;
  3188. //--------------------------------------------------------------------------
  3189. end.