Vertex Index Buffer.cpp 133 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842
  1. /******************************************************************************/
  2. #include "stdafx.h"
  3. #include "../Shaders/!Header CPU.h"
  4. namespace EE{
  5. /******************************************************************************
  6. GL_ES does not support VI._vtx_drawing because:
  7. -'glDrawElements' does not have place for '_vtx_drawing'
  8. -'glDrawElementsBaseVertex' is needed but requires GLES 3.2 TODO: add in the future
  9. 'glMapBufferRange' requires GL3.0 and GLES3.0
  10. Can't use GL_MAP_PERSISTENT_BIT because it requires GL4.4+
  11. GL ES may not support Half / F16 / GL_HALF_FLOAT / Float16 !!
  12. /******************************************************************************/
  13. // define following using defines instead of enum, so they can be used in preprocessor
  14. #if DX9 || DX11 || DX12
  15. #define MEM (32*1024)
  16. #define BUFFERS 1
  17. #elif GL
  18. #define GL_LOCK_SUB 0
  19. #define GL_LOCK_SUB_RESET_PART 1
  20. #define GL_LOCK_SUB_RESET_FULL 2
  21. #define GL_LOCK_SUB_RESET_PART_FROM 3
  22. #define GL_LOCK_SUB_RESET_FULL_FROM 4
  23. #define GL_LOCK_SUB_RING 5
  24. #define GL_LOCK_SUB_RING_RESET 6
  25. #define GL_LOCK_SUB_RING_RESET_FROM 7
  26. #define GL_LOCK_MAP 8
  27. #define GL_LOCK_MAP_RING 9
  28. #define GL_LOCK_NUM 10
  29. // TODO: test on newer hardware
  30. #if WINDOWS // tested on GeForce 650m GT
  31. #define MEM (32*1024)
  32. #define BUFFERS 1
  33. #define GL_VI_LOCK GL_LOCK_MAP_RING
  34. #elif MAC // tested on MacBook Air Intel HD 5000
  35. #define MEM (32*1024)
  36. #define BUFFERS 1
  37. #define GL_VI_LOCK GL_LOCK_SUB_RESET_PART_FROM // perf. similar to GL_LOCK_MAP
  38. #elif LINUX // untested
  39. #define MEM (32*1024)
  40. #define BUFFERS 1
  41. #define GL_VI_LOCK GL_LOCK_MAP_RING
  42. #elif ANDROID // tested on Note 4
  43. #define MEM (32*1024)
  44. #define BUFFERS 1
  45. #define GL_VI_LOCK GL_LOCK_SUB_RESET_PART_FROM // perf. similar to GL_LOCK_MAP (however on GLES2 map is not supported and defaults to slow GL_LOCK_SUB)
  46. #elif IOS // tested on iPad Mini 2
  47. #define MEM (8*1024)
  48. #define BUFFERS 1024
  49. #define GL_VI_LOCK GL_LOCK_SUB
  50. #elif WEB // untested
  51. #define MEM (32*1024)
  52. #define BUFFERS 1
  53. #define GL_VI_LOCK GL_LOCK_SUB_RESET_PART_FROM // Map is not available on WebGL - https://www.khronos.org/registry/webgl/specs/latest/2.0/#5.14
  54. #else
  55. #error
  56. #endif
  57. #endif
  58. #if GL
  59. #define BUFFERS_USE BUFFERS // 'BUFFERS' is the max amount of buffers allocated at app startup, but 'BUFFERS_USE' is the amount we want to use (can be lower for resting)
  60. #define GL_DYNAMIC GL_STREAM_DRAW // same performance as GL_DYNAMIC_DRAW
  61. #define GL_WRITE_ONLY 0x88B9
  62. #endif
  63. #if 0 // Test
  64. #pragma message("!! Warning: Use this only for debugging !!")
  65. // set defaults
  66. #ifndef BUFFERS
  67. #define BUFFERS 1
  68. #endif
  69. #ifndef GL_VI_LOCK
  70. #define GL_VI_LOCK GL_LOCK_SUB
  71. #endif
  72. Int VIMem =MEM;
  73. Int VIBuffers=BUFFERS;
  74. Int VILock =GL_VI_LOCK;
  75. // clear defaults and make them variable
  76. #undef MEM
  77. #undef BUFFERS
  78. #undef BUFFERS_USE
  79. #undef GL_VI_LOCK
  80. #define MEM VIMem
  81. #define BUFFERS 1024
  82. #define BUFFERS_USE VIBuffers
  83. #define GL_VI_LOCK VILock
  84. void VISet(Int mem, Int buffers, Int lock)
  85. {
  86. Clamp(mem , 1024, 1024*1024);
  87. Clamp(buffers, 1, BUFFERS);
  88. Clamp(lock , 0, GL_LOCK_NUM-1);
  89. if(VIMem!=mem || VIBuffers!=buffers || VILock!=lock)
  90. {
  91. VI.lost(); // call before changing params
  92. VIMem =mem;
  93. VIBuffers=buffers;
  94. VILock =lock;
  95. VI.reset();
  96. }
  97. }
  98. #endif
  99. #if GL
  100. #define GL_RING (GL_VI_LOCK==GL_LOCK_SUB_RING || GL_VI_LOCK==GL_LOCK_SUB_RING_RESET || GL_VI_LOCK==GL_LOCK_SUB_RING_RESET_FROM || GL_VI_LOCK==GL_LOCK_MAP_RING)
  101. static INLINE Bool IsMap(Bool dynamic) {return GL_VI_LOCK>=GL_LOCK_MAP && D.notShaderModelGLES2() && dynamic;}
  102. #endif
  103. #if BUFFERS>1
  104. #if GL
  105. static VtxFormatGL *VF;
  106. #endif
  107. static VtxBuf VB[BUFFERS], *VI_vb=&VB[0];
  108. //static IndBuf IB[BUFFERS], *VI_ib=&IB[0];
  109. #endif
  110. /******************************************************************************/
  111. static Int Compare(C VtxFormatKey &a, C VtxFormatKey &b)
  112. {
  113. if(a.flag <b.flag )return -1;
  114. if(a.flag >b.flag )return +1;
  115. if(a.compress<b.compress)return -1;
  116. if(a.compress>b.compress)return +1;
  117. return 0;
  118. }
  119. static Bool Create(VtxFormat &vf, C VtxFormatKey &key, Ptr) {return vf.create(key.flag, key.compress);}
  120. /******************************************************************************/
  121. IndBuf IndBuf16384Quads, IndBufBorder, IndBufPanel, IndBufPanelEx, IndBufRectBorder, IndBufRectShaded;
  122. VtxIndBuf VI;
  123. ThreadSafeMap<VtxFormatKey, VtxFormat> VtxFormats(Compare, Create);
  124. /******************************************************************************
  125. 255.0 scales (and not 256.0) are correct:
  126. https://msdn.microsoft.com/en-us/library/windows/desktop/bb173059%28v=vs.85%29.aspx
  127. https://msdn.microsoft.com/en-us/library/windows/desktop/bb322868%28v=vs.85%29.aspx
  128. The following correspond to 8-bit mapping of -1..1 float
  129. /******************************************************************************/
  130. #define UNSIGNED_N1 0 // -1
  131. #define UNSIGNED_0 128 // ~0, there is no exact zero, because 127/255.0=0.498039216, 128/255.0=0.501960784, and both are offsetted by -0.5, giving -0.001960784 and 0.001960784, however 128 is chosen to achieve same value as signed version, because converting signed/unsigned is done by adding 128, then Byte(UNSIGNED_0+128)==0 give signed zero, an exact match
  132. #define UNSIGNED_1 255 // +1
  133. #define UNSIGNED_ZP(x) ((x)>=UNSIGNED_0) // if zero or positive
  134. #define SIGNED_N1 128 // -1, this could also be 129 because both values give -1, however we want same value as unsigned version, because converting signed/unsigned is done by adding 128
  135. #define SIGNED_0 0 // 0
  136. #define SIGNED_1 127 // +1
  137. #define SIGNED_ZP(x) ((x)<=SIGNED_1) // if zero or positive
  138. Vec UByte4ToNrm(C VecB4 &v) {return !Vec(UByteToSFlt(v.x), UByteToSFlt(v.y), UByteToSFlt(v.z));}
  139. void UByte4ToTan(C VecB4 &v, Vec *tan, Vec *bin, C Vec *nrm)
  140. {
  141. Vec t=UByte4ToNrm(v);
  142. if( tan)*tan=t;
  143. if( bin)
  144. {
  145. if(nrm)*bin=Cross(*nrm, t)*SignBool(UNSIGNED_ZP(v.w));
  146. else *bin=PerpN(t);
  147. }
  148. }
  149. VecB4 NrmToUByte4(C Vec &v) {return VecB4(SFltToUByte(v.x), SFltToUByte(v.y), SFltToUByte(v.z), UNSIGNED_0);}
  150. VecB4 TanToUByte4(C Vec &v) {return VecB4(SFltToUByte(v.x), SFltToUByte(v.y), SFltToUByte(v.z), UNSIGNED_1);}
  151. VecB4 TBNToUByte4(C Vec *tan, C Vec *bin, C Vec *nrm)
  152. {
  153. Vec tan_vec;
  154. if(tan )tan_vec=*tan;else
  155. if(bin && nrm)tan_vec=Cross(*bin, *nrm);else return VecB4(UNSIGNED_0, UNSIGNED_0, UNSIGNED_0, UNSIGNED_0);
  156. VecB4 t=NrmToUByte4(tan_vec); t.w=((tan && bin && nrm && Dot(*tan, Cross(*bin, *nrm))<0) ? UNSIGNED_N1 : UNSIGNED_1);
  157. return t;
  158. }
  159. Vec SByte4ToNrm(C VecB4 &v) {return !Vec(SByteToSFlt(v.x), SByteToSFlt(v.y), SByteToSFlt(v.z));}
  160. void SByte4ToTan(C VecB4 &v, Vec *tan, Vec *bin, C Vec *nrm)
  161. {
  162. Vec t=SByte4ToNrm(v);
  163. if( tan)*tan=t;
  164. if( bin)
  165. {
  166. if(nrm)*bin=Cross(*nrm, t)*SignBool(SIGNED_ZP(v.w));
  167. else *bin=PerpN(t);
  168. }
  169. }
  170. VecB4 NrmToSByte4(C Vec &v) {return VecB4(SFltToSByte(v.x), SFltToSByte(v.y), SFltToSByte(v.z), SIGNED_0);}
  171. VecB4 TanToSByte4(C Vec &v) {return VecB4(SFltToSByte(v.x), SFltToSByte(v.y), SFltToSByte(v.z), SIGNED_1);}
  172. VecB4 TBNToSByte4(C Vec *tan, C Vec *bin, C Vec *nrm)
  173. {
  174. Vec tan_vec;
  175. if(tan )tan_vec=*tan;else
  176. if(bin && nrm)tan_vec=Cross(*bin, *nrm);else return VecB4(SIGNED_0, SIGNED_0, SIGNED_0, SIGNED_0);
  177. VecB4 t=NrmToSByte4(tan_vec); t.w=((tan && bin && nrm && Dot(*tan, Cross(*bin, *nrm))<0) ? SIGNED_N1 : SIGNED_1);
  178. return t;
  179. }
  180. /******************************************************************************/
  181. // VERTEX FORMAT
  182. /******************************************************************************/
  183. #if DX9
  184. static inline void Set(D3DVERTEXELEMENT9 &ve, Int offset, Byte type, Byte usage, Byte index=0)
  185. {
  186. ve.Stream=0;
  187. ve.Offset=offset;
  188. ve.Type =type;
  189. ve.Method=D3DDECLMETHOD_DEFAULT;
  190. ve.Usage =usage;
  191. ve.UsageIndex=index;
  192. }
  193. static inline void End(D3DVERTEXELEMENT9 &ve)
  194. {
  195. ve.Stream=0xFF;
  196. ve.Offset=0;
  197. ve.Type =D3DDECLTYPE_UNUSED;
  198. ve.Method=0;
  199. ve.Usage =0;
  200. ve.UsageIndex=0;
  201. }
  202. Bool SetVtxFormatFromVtxDecl(IDirect3DVertexDeclaration9 *vf, D3DVERTEXELEMENT9 (&ve)[MAX_FVF_DECL_SIZE])
  203. {
  204. UINT elements=0;
  205. return vf ? OK(vf->GetDeclaration(ve, &elements)) : false;
  206. }
  207. #elif DX11
  208. static inline void Set(D3D11_INPUT_ELEMENT_DESC &ve, Int offset, DXGI_FORMAT format, CChar8 *name, Byte index=0)
  209. {
  210. ve.AlignedByteOffset=offset;
  211. ve.Format=format;
  212. ve.InputSlot=0;
  213. ve.InputSlotClass=D3D11_INPUT_PER_VERTEX_DATA;
  214. ve.InstanceDataStepRate=0;
  215. ve.SemanticIndex=index;
  216. ve.SemanticName=name;
  217. }
  218. #endif
  219. /******************************************************************************/
  220. VtxFormat& VtxFormat::del()
  221. {
  222. if(vf)
  223. {
  224. SafeSyncLocker lock(D._lock);
  225. if(D._vf==vf)D.vf(null);
  226. #if DX9 || DX11
  227. if(vf){if(D.created())vf->Release(); vf=null;} // clear while in lock
  228. #elif GL
  229. Delete(vf);
  230. #endif
  231. }
  232. return T;
  233. }
  234. #if DX9
  235. Bool VtxFormat::create(D3DVERTEXELEMENT9 ve[])
  236. {
  237. SyncLocker locker(D._lock);
  238. del();
  239. if(D3D)return OK(D3D->CreateVertexDeclaration(ve, &vf));
  240. return false;
  241. }
  242. #elif DX11
  243. // following 'VS_Code' is a byte code of a vertex shader from "DX10+ Input Layout.cpp", look around the sources for 'VS_Code' name on how to obtain the code (the code needs to be updated everytime VtxInput is changed)
  244. static Byte VS_Code[784]={68,88,66,67,63,223,95,34,222,170,1,4,254,68,111,21,173,124,17,124,1,0,0,0,16,3,0,0,5,0,0,0,52,0,0,0,128,0,0,0,28,2,0,0,80,2,0,0,148,2,0,0,82,68,69,70,68,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,28,0,0,0,0,4,254,255,0,145,0,0,28,0,0,0,77,105,99,114,111,115,111,102,116,32,40,82,41,32,72,76,83,76,32,83,104,97,100,101,114,32,67,111,109,112,105,108,101,114,32,49,48,46,49,0,73,83,71,78,148,1,0,0,13,0,0,0,8,0,0,0,64,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,0,0,0,0,15,15,0,0,64,1,0,0,1,0,0,0,0,0,0,0,3,0,0,0,1,0,0,0,7,0,0,0,73,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,2,0,0,0,7,0,0,0,80,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,3,0,0,0,15,0,0,0,88,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,4,0,0,0,3,0,0,0,88,1,0,0,1,0,0,0,0,0,0,0,3,0,0,0,5,0,0,0,3,0,0,0,88,1,0,0,2,0,0,0,0,0,0,0,3,0,0,0,6,0,0,0,3,0,0,0,97,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,7,0,0,0,1,0,0,0,103,1,0,0,0,0,0,0,0,0,0,0,1,0,0,0,8,0,0,0,15,0,0,0,116,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,9,0,0,0,15,0,0,0,128,1,0,0,0,0,0,0,0,0,0,0,3,0,0,0,10,0,0,0,15,0,0,0,128,1,0,0,1,0,0,0,0,0,0,0,3,0,0,0,11,0,0,0,15,0,0,0,134,1,0,0,0,0,0,0,8,0,0,0,1,0,0,0,12,0,0,0,1,0,0,0,80,79,83,73,84,73,79,78,0,78,79,82,77,65,76,0,84,65,78,71,69,78,84,0,84,69,88,67,79,79,82,68,0,80,83,73,90,69,0,66,76,69,78,68,73,78,68,73,67,69,83,0,66,76,69,78,68,87,69,73,71,72,84,0,67,79,76,79,82,0,83,86,95,73,110,115,116,97,110,99,101,73,68,0,79,83,71,78,44,0,0,0,1,0,0,0,8,0,0,0,32,0,0,0,0,0,0,0,1,0,0,0,3,0,0,0,0,0,0,0,15,0,0,0,83,86,95,80,111,115,105,116,105,111,110,0,83,72,68,82,60,0,0,0,64,0,1,0,15,0,0,0,95,0,0,3,242,16,16,0,0,0,0,0,103,0,0,4,242,32,16,0,0,0,0,0,1,0,0,0,54,0,0,5,242,32,16,0,0,0,0,0,70,30,16,0,0,0,0,0,62,0,0,1,83,84,65,84,116,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
  245. Bool VtxFormat::create(D3D11_INPUT_ELEMENT_DESC ve[], Int elms)
  246. {
  247. //SyncLocker locker(D._lock); lock not needed for DX11 'D3D'
  248. del();
  249. if(D3D)return OK(D3D->CreateInputLayout(ve, elms, VS_Code, Elms(VS_Code), &vf));
  250. return false;
  251. }
  252. #elif GL
  253. GL_VTX_SEMANTIC VtxSemanticToIndex(Int semantic)
  254. {
  255. if(D._max_vtx_attribs<=semantic) // if GPU doesn't support this semantic
  256. {
  257. switch(semantic)
  258. {
  259. case GL_VTX_MATERIAL: semantic=GL_VTX_BONE ; break; // re-use the same index, this assumes that material is used only for terrain, and no terrain is skinned
  260. case GL_VTX_HLP : semantic=GL_VTX_TEX1 ; break; // re-use the same index, this assumes that (helper position used for animating tree-leafs/grass) will not have tex1
  261. case GL_VTX_SIZE : semantic=GL_VTX_WEIGHT ; break; // re-use the same index, this assumes that (helper position used for animating tree-leafs/grass) will not have bone weights
  262. case GL_VTX_TEX2 : semantic=GL_VTX_MATERIAL; break; // re-use the same index, this assumes that shaders using 3rd set of UV's don't use material blending
  263. }
  264. if(D._max_vtx_attribs<=semantic)semantic=D._max_vtx_attribs-1; // if it still doesn't support it
  265. }
  266. return GL_VTX_SEMANTIC(semantic);
  267. }
  268. void BindIndexBuffer(UInt buf)
  269. {
  270. if(D.notShaderModelGLES2())glBindVertexArray(0); // !! have to clear VAO before calling "glBindBuffer(GL_ELEMENT_ARRAY_BUFFER" to make sure it won't modify it, not needed for 'GL_ARRAY_BUFFER' because those are bound only with 'glVertexAttribPointer' !!
  271. glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, buf);
  272. }
  273. void VtxFormatGL::del()
  274. {
  275. if(vao)
  276. {
  277. SafeSyncLocker lock(D._lock); if(D.created())glDeleteVertexArrays(1, &vao); vao=0; // this method will be called only on the main thread (in the 'VtxFormats.del'), so it's OK to always call 'glDeleteVertexArrays', clear while in lock
  278. }
  279. elms.del();
  280. }
  281. Bool VtxFormatGL::create(C MemPtrN<Elm, 32> &elms)
  282. {
  283. T.elms =elms;
  284. T.vtx_size=0;
  285. FREPA(T.elms)
  286. {
  287. Byte component_size;
  288. switch(T.elms[i].component_type)
  289. {
  290. case GL_BYTE : case GL_UNSIGNED_BYTE : component_size=1; break;
  291. case GL_SHORT : case GL_UNSIGNED_SHORT: component_size=2; break;
  292. case GL_HALF_FLOAT: component_size=2; break;
  293. case GL_INT : case GL_UNSIGNED_INT : component_size=4; break;
  294. case GL_FLOAT : component_size=4; break;
  295. #ifdef GL_DOUBLE
  296. case GL_DOUBLE : component_size=8; break;
  297. #endif
  298. default : Exit("Unrecognized OpenGL Component Type"); return false;
  299. }
  300. T.elms[i].semantic=VtxSemanticToIndex(T.elms[i].semantic);
  301. T.vtx_size+=component_size*T.elms[i].component_num;
  302. }
  303. return true;
  304. }
  305. void VtxFormatGL::disable()C
  306. {
  307. REPA(elms)glDisableVertexAttribArray(elms[i].semantic);
  308. }
  309. void VtxFormatGL::enableSet()C
  310. {
  311. REPA(elms)
  312. {
  313. C Elm &ve=elms[i];
  314. glEnableVertexAttribArray(ve.semantic);
  315. glVertexAttribPointer (ve.semantic, ve.component_num, ve.component_type, ve.component_normalize, vtx_size, (CPtr)ve.offset);
  316. }
  317. }
  318. void VtxFormatGL::bind(C VtxBuf &vb) // this is called only on the main thread
  319. {
  320. if(D.notShaderModelGLES2()) // VAO
  321. {
  322. #if GL_LOCK
  323. SyncLocker lock(D._lock);
  324. #endif
  325. if(!vao)
  326. {
  327. glGenVertexArrays(1, &vao);
  328. if(!vao)Exit("Can't create VAO");
  329. }
  330. glBindVertexArray(vao);
  331. // no need to do any disabling, because once vtx format is created, its members are always the same, we just need to 'enableSet' to the new VBO
  332. vb.set(); // have to call this first
  333. enableSet();
  334. glBindVertexArray(0); // disable VAO so binding IB will not modify this VAO, this is not strictly needed, because all IB bindings use either 'BindIndexBuffer' which clears VAO, or are done during drawing when correct VAO is already set, but leave it just in case
  335. }
  336. }
  337. Bool VtxFormat::create(C MemPtrN<VtxFormatGL::Elm, 32> &elms) {if(!vf)New(vf); return vf->create(elms);}
  338. void VtxFormat::bind(C VtxBuf &vb) {if(vf)vf->bind(vb);}
  339. #endif
  340. Bool VtxFormat::create(UInt flag, UInt compress)
  341. {
  342. // TODO: use R10G10B10A2 for compressed Nrm and Tan, however there's no signed format for that, so probably have to forget it
  343. #if DX9
  344. D3DVERTEXELEMENT9 ve[MAX_FVF_DECL_SIZE];
  345. Int i=0, ofs=0;
  346. if(flag& VTX_POS ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT3 , D3DDECLUSAGE_POSITION , 0); ofs+=SIZE(Vec );}
  347. if(compress&VTX_COMPRESS_NRM ){if(flag& VTX_NRM ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_NORMAL ); ofs+=SIZE(VecB4);}}
  348. else {if(flag& VTX_NRM ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT3 , D3DDECLUSAGE_NORMAL ); ofs+=SIZE(Vec );}}
  349. if(compress&VTX_COMPRESS_TAN_BIN){if(flag&VTX_TAN_BIN ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_TANGENT ); ofs+=SIZE(VecB4);}}
  350. else {if(flag&VTX_TAN ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT3 , D3DDECLUSAGE_TANGENT ); ofs+=SIZE(Vec );}
  351. if(flag&VTX_BIN ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT3 , D3DDECLUSAGE_BINORMAL ); ofs+=SIZE(Vec );}}
  352. if(flag& VTX_HLP ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT3 , D3DDECLUSAGE_POSITION , 1); ofs+=SIZE(Vec );}
  353. if(compress&VTX_COMPRESS_TEX_8 ){if(flag& VTX_TEX0 ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_TEXCOORD , 0); ofs+=SIZE(VecB4);}
  354. if(flag& VTX_TEX1 ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_TEXCOORD , 1); ofs+=SIZE(VecB4);}
  355. if(flag& VTX_TEX2 ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_TEXCOORD , 2); ofs+=SIZE(VecB4);}}else
  356. if(compress&VTX_COMPRESS_TEX ){if(flag& VTX_TEX0 ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT16_2, D3DDECLUSAGE_TEXCOORD , 0); ofs+=SIZE(VecH2);}
  357. if(flag& VTX_TEX1 ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT16_2, D3DDECLUSAGE_TEXCOORD , 1); ofs+=SIZE(VecH2);}
  358. if(flag& VTX_TEX2 ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT16_2, D3DDECLUSAGE_TEXCOORD , 2); ofs+=SIZE(VecH2);}}else
  359. {if(flag& VTX_TEX0 ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT2 , D3DDECLUSAGE_TEXCOORD , 0); ofs+=SIZE(Vec2 );}
  360. if(flag& VTX_TEX1 ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT2 , D3DDECLUSAGE_TEXCOORD , 1); ofs+=SIZE(Vec2 );}
  361. if(flag& VTX_TEX2 ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT2 , D3DDECLUSAGE_TEXCOORD , 2); ofs+=SIZE(Vec2 );}}
  362. if(flag& VTX_MATRIX ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4 , D3DDECLUSAGE_BLENDINDICES ); ofs+=SIZE(VecB4);}
  363. if(flag& VTX_BLEND ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_BLENDWEIGHT ); ofs+=SIZE(VecB4);}
  364. if(flag& VTX_SIZE ){Set(ve[i++], ofs, D3DDECLTYPE_FLOAT1 , D3DDECLUSAGE_PSIZE ); ofs+=SIZE(Flt );}
  365. if(flag& VTX_MATERIAL){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_COLOR , 0); ofs+=SIZE(VecB4);}
  366. if(flag& VTX_COLOR ){Set(ve[i++], ofs, D3DDECLTYPE_UBYTE4N , D3DDECLUSAGE_COLOR , 1); ofs+=SIZE(Color);}
  367. End(ve[i ]);
  368. return create(ve);
  369. #elif DX11
  370. D3D11_INPUT_ELEMENT_DESC ve[D3D11_IA_VERTEX_INPUT_STRUCTURE_ELEMENT_COUNT];
  371. const DXGI_FORMAT nrm_tan=(D.meshStorageSigned() ? DXGI_FORMAT_R8G8B8A8_SNORM : DXGI_FORMAT_R8G8B8A8_UNORM);
  372. Int i=0, ofs=0;
  373. Set(ve[i++], ofs, DXGI_FORMAT_R32G32B32_FLOAT, "POSITION" , 0); if(flag&VTX_POS )ofs+=SIZE(Vec );
  374. if(compress&VTX_COMPRESS_NRM ){Set(ve[i++], ofs, nrm_tan , "NORMAL" , 0); if(flag&VTX_NRM )ofs+=SIZE(VecB4);}
  375. else {Set(ve[i++], ofs, DXGI_FORMAT_R32G32B32_FLOAT, "NORMAL" , 0); if(flag&VTX_NRM )ofs+=SIZE(Vec );}
  376. if(compress&VTX_COMPRESS_TAN_BIN){Set(ve[i++], ofs, nrm_tan , "TANGENT" , 0); if(flag&VTX_TAN_BIN )ofs+=SIZE(VecB4);}
  377. else {Set(ve[i++], ofs, DXGI_FORMAT_R32G32B32_FLOAT, "TANGENT" , 0); if(flag&VTX_TAN )ofs+=SIZE(Vec );
  378. Set(ve[i++], ofs, DXGI_FORMAT_R32G32B32_FLOAT, "BINORMAL" , 0); if(flag&VTX_BIN )ofs+=SIZE(Vec );}
  379. Set(ve[i++], ofs, DXGI_FORMAT_R32G32B32_FLOAT, "POSITION" , 1); if(flag&VTX_HLP )ofs+=SIZE(Vec );
  380. if(compress&VTX_COMPRESS_TEX_8 ){Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UNORM , "TEXCOORD" , 0); if(flag&VTX_TEX0 )ofs+=SIZE(VecB4);
  381. Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UNORM , "TEXCOORD" , 1); if(flag&VTX_TEX1 )ofs+=SIZE(VecB4);
  382. Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UNORM , "TEXCOORD" , 2); if(flag&VTX_TEX2 )ofs+=SIZE(VecB4);}else
  383. if(compress&VTX_COMPRESS_TEX ){Set(ve[i++], ofs, DXGI_FORMAT_R16G16_FLOAT , "TEXCOORD" , 0); if(flag&VTX_TEX0 )ofs+=SIZE(VecH2);
  384. Set(ve[i++], ofs, DXGI_FORMAT_R16G16_FLOAT , "TEXCOORD" , 1); if(flag&VTX_TEX1 )ofs+=SIZE(VecH2);
  385. Set(ve[i++], ofs, DXGI_FORMAT_R16G16_FLOAT , "TEXCOORD" , 2); if(flag&VTX_TEX2 )ofs+=SIZE(VecH2);}else
  386. {Set(ve[i++], ofs, DXGI_FORMAT_R32G32_FLOAT , "TEXCOORD" , 0); if(flag&VTX_TEX0 )ofs+=SIZE(Vec2 );
  387. Set(ve[i++], ofs, DXGI_FORMAT_R32G32_FLOAT , "TEXCOORD" , 1); if(flag&VTX_TEX1 )ofs+=SIZE(Vec2 );
  388. Set(ve[i++], ofs, DXGI_FORMAT_R32G32_FLOAT , "TEXCOORD" , 2); if(flag&VTX_TEX2 )ofs+=SIZE(Vec2 );}
  389. Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UINT , "BLENDINDICES", 0); if(flag&VTX_MATRIX )ofs+=SIZE(VecB4);
  390. Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UNORM , "BLENDWEIGHT" , 0); if(flag&VTX_BLEND )ofs+=SIZE(VecB4);
  391. Set(ve[i++], ofs, DXGI_FORMAT_R32_FLOAT , "PSIZE" , 0); if(flag&VTX_SIZE )ofs+=SIZE(Flt );
  392. Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UNORM , "COLOR" , 0); if(flag&VTX_MATERIAL)ofs+=SIZE(VecB4);
  393. Set(ve[i++], ofs, DXGI_FORMAT_R8G8B8A8_UNORM , "COLOR" , 1); if(flag&VTX_COLOR )ofs+=SIZE(Color);
  394. return create(ve, i);
  395. #elif GL
  396. MemtN<VtxFormatGL::Elm, 32> ve;
  397. Int ofs=0;
  398. if(flag&VTX_POS ){ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, ofs); ofs+=SIZE(Vec );}
  399. if(compress&VTX_COMPRESS_NRM ){if(flag&VTX_NRM ){ve.New().set(GL_VTX_NRM , 4, GL_BYTE , true , ofs); ofs+=SIZE(VecB4);}}
  400. else {if(flag&VTX_NRM ){ve.New().set(GL_VTX_NRM , 3, GL_FLOAT , false, ofs); ofs+=SIZE(Vec );}}
  401. if(compress&VTX_COMPRESS_TAN_BIN){if(flag&VTX_TAN_BIN ){ve.New().set(GL_VTX_TAN , 4, GL_BYTE , true , ofs); ofs+=SIZE(VecB4);}}
  402. else {if(flag&VTX_TAN ){ve.New().set(GL_VTX_TAN , 3, GL_FLOAT , false, ofs); ofs+=SIZE(Vec );}
  403. if(flag&VTX_BIN ){ ofs+=SIZE(Vec );}}
  404. if(flag&VTX_HLP ){ve.New().set(GL_VTX_HLP , 3, GL_FLOAT , false, ofs); ofs+=SIZE(Vec );}
  405. if(compress&VTX_COMPRESS_TEX_8 ){if(flag&VTX_TEX0 ){ve.New().set(GL_VTX_TEX0 , 4, GL_UNSIGNED_BYTE, true , ofs); ofs+=SIZE(VecB4);}
  406. if(flag&VTX_TEX1 ){ve.New().set(GL_VTX_TEX1 , 4, GL_UNSIGNED_BYTE, true , ofs); ofs+=SIZE(VecB4);}
  407. if(flag&VTX_TEX2 ){ve.New().set(GL_VTX_TEX2 , 4, GL_UNSIGNED_BYTE, true , ofs); ofs+=SIZE(VecB4);}}else
  408. if(compress&VTX_COMPRESS_TEX ){if(flag&VTX_TEX0 ){ve.New().set(GL_VTX_TEX0 , 2, GL_HALF_FLOAT , false, ofs); ofs+=SIZE(VecH2);}
  409. if(flag&VTX_TEX1 ){ve.New().set(GL_VTX_TEX1 , 2, GL_HALF_FLOAT , false, ofs); ofs+=SIZE(VecH2);}
  410. if(flag&VTX_TEX2 ){ve.New().set(GL_VTX_TEX2 , 2, GL_HALF_FLOAT , false, ofs); ofs+=SIZE(VecH2);}}else
  411. {if(flag&VTX_TEX0 ){ve.New().set(GL_VTX_TEX0 , 2, GL_FLOAT , false, ofs); ofs+=SIZE(Vec2 );}
  412. if(flag&VTX_TEX1 ){ve.New().set(GL_VTX_TEX1 , 2, GL_FLOAT , false, ofs); ofs+=SIZE(Vec2 );}
  413. if(flag&VTX_TEX2 ){ve.New().set(GL_VTX_TEX2 , 2, GL_FLOAT , false, ofs); ofs+=SIZE(Vec2 );}}
  414. if(flag&VTX_MATRIX ){ve.New().set(GL_VTX_BONE , 4, GL_UNSIGNED_BYTE, false, ofs); ofs+=SIZE(VecB4);}
  415. if(flag&VTX_BLEND ){ve.New().set(GL_VTX_WEIGHT , 4, GL_UNSIGNED_BYTE, true , ofs); ofs+=SIZE(VecB4);}
  416. if(flag&VTX_SIZE ){ve.New().set(GL_VTX_SIZE , 1, GL_FLOAT , false, ofs); ofs+=SIZE(Flt );}
  417. if(flag&VTX_MATERIAL){ve.New().set(GL_VTX_MATERIAL, 4, GL_UNSIGNED_BYTE, true , ofs); ofs+=SIZE(VecB4);}
  418. if(flag&VTX_COLOR ){ve.New().set(GL_VTX_COLOR , 4, GL_UNSIGNED_BYTE, true , ofs); ofs+=SIZE(Color);}
  419. return create(ve);
  420. #endif
  421. return false;
  422. }
  423. /******************************************************************************/
  424. // VERTEX BUFFER
  425. /******************************************************************************/
  426. VtxBuf& VtxBuf::del()
  427. {
  428. unlock();
  429. if(_buf)
  430. {
  431. #if DX9 || GL_LOCK // lock not needed for DX11 'Release'
  432. SafeSyncLocker lock(D._lock);
  433. #endif
  434. #if DX9 || DX11
  435. if(_buf){if(D.created())_buf->Release(); _buf=null;} // clear while in lock
  436. #elif GL
  437. if(D.created())glDeleteBuffers(1, &_buf); _buf=0; // clear while in lock
  438. if(!IsMap(_dynamic))Free(_data);
  439. #endif
  440. }
  441. Zero(T); return T;
  442. }
  443. IndBuf& IndBuf::del()
  444. {
  445. unlock();
  446. if(_buf)
  447. {
  448. #if DX9 || GL_LOCK // lock not needed for DX11 'Release'
  449. SafeSyncLocker lock(D._lock);
  450. #endif
  451. #if DX9 || DX11
  452. if(_buf){if(D.created())_buf->Release(); _buf=null;} // clear while in lock
  453. #elif GL
  454. if(D.created())glDeleteBuffers(1, &_buf); _buf=0; // clear while in lock
  455. if(!IsMap(_dynamic))Free(_data);
  456. #endif
  457. }
  458. Zero(T); return T;
  459. }
  460. /******************************************************************************/
  461. Bool VtxBuf::createRaw(Int memory_size, Bool dynamic, CPtr data)
  462. {
  463. #if 0 // we can't do this here, because 'createRaw' does not set any info about 'vtxs', 'vtxSize' or 'memUsage', and in 'VI._vb' those params always change, instead these checks are in 'createNum'
  464. if(memUsage()==memory_size && T._dynamic==dynamic && !_lock_count) // if the buffer is already created and matches what we want
  465. if(!data || setFrom(data, memory_size))return true; // if 'setFrom' failed then try creating new below
  466. #endif
  467. if(memory_size<=0){del(); return !memory_size;}
  468. #if DX9 || GL_LOCK // lock not needed for DX11 'D3D'
  469. SyncLocker locker(D._lock);
  470. #endif
  471. del();
  472. if(D.created())
  473. {
  474. T._dynamic=dynamic;
  475. #if DX9
  476. if(OK(D3D->CreateVertexBuffer(memory_size, dynamic ? D3DUSAGE_DYNAMIC|D3DUSAGE_WRITEONLY : 0, 0, dynamic ? D3DPOOL_DEFAULT : D3DPOOL_MANAGED, &_buf, null)))
  477. if(!data || setFrom(data, memory_size))return true;
  478. #elif DX11
  479. D3D11_BUFFER_DESC desc;
  480. desc.ByteWidth =memory_size;
  481. desc.Usage =(dynamic ? D3D11_USAGE_DYNAMIC : D3D11_USAGE_DEFAULT);
  482. desc.CPUAccessFlags =(dynamic ? D3D11_CPU_ACCESS_WRITE : 0);
  483. desc.BindFlags =D3D11_BIND_VERTEX_BUFFER;
  484. desc.MiscFlags =0;
  485. desc.StructureByteStride=0;
  486. D3D11_SUBRESOURCE_DATA res_data, *initial_data=null;
  487. if(data)
  488. {
  489. res_data.pSysMem=data;
  490. res_data.SysMemPitch=res_data.SysMemSlicePitch=0;
  491. initial_data=&res_data;
  492. }
  493. if(OK(D3D->CreateBuffer(&desc, initial_data, &_buf)))return true;
  494. #elif GL
  495. glGenBuffers(1, &_buf);
  496. if(_buf)
  497. {
  498. glBindBuffer(GL_ARRAY_BUFFER, _buf);
  499. glBufferData(GL_ARRAY_BUFFER, memory_size, data, dynamic ? GL_DYNAMIC : GL_STATIC_DRAW);
  500. glFlush(); // to make sure that the data was initialized, in case it'll be accessed on a secondary thread
  501. if(!IsMap(dynamic) && (dynamic || GL_ES)) // never allocate for Map, allocate for dynamic or for GL_ES for which we can't read memory from GL
  502. {
  503. Alloc(_data, CeilGL(memory_size)); if(data)CopyFast(_data, data, memory_size);
  504. }
  505. return true;
  506. }
  507. #endif
  508. }
  509. del(); return false;
  510. }
  511. Bool IndBuf::create(Int indexes, Bool bit16, Bool dynamic, CPtr data)
  512. {
  513. if(T._ind_num==indexes && T.bit16()==bit16 && T._dynamic==dynamic && !_lock_count) // if the buffer is already created and matches what we want
  514. if(!data || setFrom(data))return true; // if 'setFrom' failed then try creating new below
  515. if(indexes<=0){del(); return !indexes;}
  516. #if DX9 || GL_LOCK // lock not needed for DX11 'D3D'
  517. SyncLocker locker(D._lock);
  518. #endif
  519. del();
  520. if(D.created())
  521. {
  522. T._dynamic=dynamic;
  523. Int memory_size=indexes*(bit16 ? 2 : 4);
  524. #if DX9
  525. if(OK(D3D->CreateIndexBuffer(memory_size, dynamic ? D3DUSAGE_DYNAMIC|D3DUSAGE_WRITEONLY : 0, bit16 ? D3DFMT_INDEX16 : D3DFMT_INDEX32, dynamic ? D3DPOOL_DEFAULT : D3DPOOL_MANAGED, &_buf, null)))
  526. {
  527. T._bit16 =bit16 ;
  528. T._ind_num=indexes;
  529. if(!data || setFrom(data))return true;
  530. }
  531. #elif DX11
  532. D3D11_BUFFER_DESC desc;
  533. desc.ByteWidth =memory_size;
  534. desc.Usage =(dynamic ? D3D11_USAGE_DYNAMIC : D3D11_USAGE_DEFAULT);
  535. desc.CPUAccessFlags=(dynamic ? D3D11_CPU_ACCESS_WRITE : 0);
  536. desc.BindFlags =D3D11_BIND_INDEX_BUFFER;
  537. desc.MiscFlags =0;
  538. desc.StructureByteStride=0;
  539. D3D11_SUBRESOURCE_DATA res_data, *initial_data=null;
  540. if(data)
  541. {
  542. res_data.pSysMem=data;
  543. res_data.SysMemPitch=res_data.SysMemSlicePitch=0;
  544. initial_data=&res_data;
  545. }
  546. if(OK(D3D->CreateBuffer(&desc, initial_data, &_buf)))
  547. {
  548. T._bit16 =bit16 ;
  549. T._ind_num=indexes;
  550. return true;
  551. }
  552. #elif GL
  553. glGenBuffers(1, &_buf);
  554. if(_buf)
  555. {
  556. BindIndexBuffer(_buf);
  557. glBufferData(GL_ELEMENT_ARRAY_BUFFER, memory_size, data, dynamic ? GL_DYNAMIC : GL_STATIC_DRAW);
  558. glFlush(); // to make sure that the data was initialized, in case it'll be accessed on a secondary thread
  559. T._bit16 =bit16 ;
  560. T._ind_num=indexes;
  561. if(!IsMap(dynamic) && (dynamic || GL_ES)) // never allocate for Map, allocate for dynamic or for GL_ES for which we can't read memory from GL
  562. {
  563. Alloc(_data, CeilGL(memory_size)); if(data)CopyFast(_data, data, memory_size);
  564. }
  565. return true;
  566. }
  567. #endif
  568. }
  569. del(); return false;
  570. }
  571. /******************************************************************************/
  572. Bool VtxBuf::createNum(Int vtx_size, Int vtx_num, Bool dynamic, CPtr data)
  573. {
  574. if(vtxSize()==vtx_size && vtxs()==vtx_num && T._dynamic==dynamic && !_lock_count) // if the buffer is already created and matches what we want
  575. if(!data || setFrom(data, memUsage()))return true; // if 'setFrom' failed then try creating new below
  576. if(createRaw(vtx_size*vtx_num, dynamic, data))
  577. {
  578. T._vtx_size=vtx_size;
  579. T._vtx_num =vtx_num ;
  580. return true;
  581. }
  582. return false;
  583. }
  584. Bool VtxBuf::create(Int vertexes, UInt flag, UInt compress, Bool dynamic)
  585. {
  586. Int size=0;
  587. if(flag&VTX_POS )size+=SIZE(Vec );
  588. if(compress&VTX_COMPRESS_NRM ){if(flag&VTX_NRM )size+=SIZE(VecB4);}
  589. else {if(flag&VTX_NRM )size+=SIZE(Vec );}
  590. if(compress&VTX_COMPRESS_TAN_BIN){if(flag&VTX_TAN_BIN )size+=SIZE(VecB4);}
  591. else {if(flag&VTX_TAN )size+=SIZE(Vec );
  592. if(flag&VTX_BIN )size+=SIZE(Vec );}
  593. if(flag&VTX_HLP )size+=SIZE(Vec );
  594. if(compress&VTX_COMPRESS_TEX_8 ){if(flag&VTX_TEX0 )size+=SIZE(VecB4);
  595. if(flag&VTX_TEX1 )size+=SIZE(VecB4);
  596. if(flag&VTX_TEX2 )size+=SIZE(VecB4);}else
  597. if(compress&VTX_COMPRESS_TEX ){if(flag&VTX_TEX0 )size+=SIZE(VecH2);
  598. if(flag&VTX_TEX1 )size+=SIZE(VecH2);
  599. if(flag&VTX_TEX2 )size+=SIZE(VecH2);}else
  600. {if(flag&VTX_TEX0 )size+=SIZE(Vec2 );
  601. if(flag&VTX_TEX1 )size+=SIZE(Vec2 );
  602. if(flag&VTX_TEX2 )size+=SIZE(Vec2 );}
  603. if(flag&VTX_MATRIX )size+=SIZE(VecB4);
  604. if(flag&VTX_BLEND )size+=SIZE(VecB4);
  605. if(flag&VTX_SIZE )size+=SIZE(Flt );
  606. if(flag&VTX_MATERIAL)size+=SIZE(VecB4);
  607. if(flag&VTX_COLOR )size+=SIZE(Color);
  608. return createNum(size, vertexes, dynamic);
  609. }
  610. /******************************************************************************/
  611. Bool VtxBuf::create(C VtxBuf &src, Int dynamic)
  612. {
  613. if(this==&src)return true;
  614. {
  615. CPtr src_data=null; if(src.is() && !(src_data=src.lockRead()))goto error;
  616. Bool ok=createNum(src.vtxSize(), src.vtxs(), (dynamic>=0) ? dynamic!=0 : src._dynamic, src_data);
  617. if(src_data)src.unlock();
  618. return ok;
  619. }
  620. error:
  621. del(); return false;
  622. }
  623. Bool IndBuf::create(C IndBuf &src, Int dynamic)
  624. {
  625. if(this==&src)return true;
  626. {
  627. CPtr src_data=null; if(src.is() && !(src_data=src.lockRead()))goto error;
  628. Bool ok=create(src._ind_num, src.bit16(), (dynamic>=0) ? dynamic!=0 : src._dynamic, src_data);
  629. if(src_data)src.unlock();
  630. return ok;
  631. }
  632. error:
  633. del(); return false;
  634. }
  635. /******************************************************************************/
  636. Byte* VtxBuf::lockDynamic()
  637. {
  638. DEBUG_ASSERT(_buf && !_lock_mode && _dynamic, "VtxBuf.lockDynamic");
  639. LOCK_MODE lock=(VI._vtx_drawing ? LOCK_APPEND : LOCK_WRITE);
  640. #if DX9
  641. Ptr data=null; _buf->Lock(0, 0, &data, (lock==LOCK_WRITE) ? D3DLOCK_DISCARD : D3DLOCK_NOOVERWRITE); T._data=(Byte*)data;
  642. #elif DX11
  643. D3D11_MAPPED_SUBRESOURCE map;
  644. if(OK(D3DC->Map(_buf, 0, (lock==LOCK_WRITE) ? D3D11_MAP_WRITE_DISCARD : D3D11_MAP_WRITE_NO_OVERWRITE, 0, &map)))_data=(Byte*)map.pData;
  645. #elif GL
  646. if(IsMap(true))
  647. {
  648. glBindBuffer (GL_ARRAY_BUFFER, _buf);
  649. if(!GL_RING) _data=(Byte*)glMapBufferRange(GL_ARRAY_BUFFER, 0, MEM , GL_MAP_WRITE_BIT|GL_MAP_FLUSH_EXPLICIT_BIT|GL_MAP_INVALIDATE_BUFFER_BIT);
  650. if( GL_RING){UInt offset=VI._vtx_drawing*_vtx_size; if(_data=(Byte*)glMapBufferRange(GL_ARRAY_BUFFER, offset, MEM-offset, GL_MAP_WRITE_BIT|GL_MAP_FLUSH_EXPLICIT_BIT|(lock==LOCK_WRITE ? GL_MAP_INVALIDATE_BUFFER_BIT : /*made things slower GL_MAP_INVALIDATE_RANGE_BIT|*/GL_MAP_UNSYNCHRONIZED_BIT)))_data-=offset;}
  651. }else
  652. {
  653. // data for dynamic is already allocated and ready to use
  654. }
  655. #endif
  656. if(_data)
  657. {
  658. T._lock_mode =lock;
  659. T._lock_count=1;
  660. }
  661. return _data;
  662. }
  663. void VtxBuf::unlockDynamic()
  664. {
  665. DEBUG_ASSERT((_lock_mode==LOCK_WRITE || _lock_mode==LOCK_APPEND) && _lock_count==1 && _dynamic, "VtxBuf.unlockDynamic");
  666. #if DX9
  667. _buf->Unlock(); _data=null;
  668. #elif DX11
  669. D3DC->Unmap(_buf, 0); _data=null;
  670. #elif GL
  671. glBindBuffer(GL_ARRAY_BUFFER, _buf);
  672. if(IsMap(true))
  673. {
  674. glFlushMappedBufferRange(GL_ARRAY_BUFFER, 0, VI._vtx_queued*_vtx_size); // we always start from zero, because values are relative to locked range
  675. glUnmapBuffer (GL_ARRAY_BUFFER);
  676. _data=null;
  677. }else
  678. switch(GL_VI_LOCK)
  679. {
  680. default : glBufferSubData(GL_ARRAY_BUFFER, 0, VI._vtx_queued*_vtx_size, _data ); break;
  681. case GL_LOCK_SUB_RESET_PART : glBufferData(GL_ARRAY_BUFFER, VI._vtx_queued*_vtx_size, null, GL_DYNAMIC); glBufferSubData(GL_ARRAY_BUFFER, 0, VI._vtx_queued*_vtx_size, _data ); break;
  682. case GL_LOCK_SUB_RESET_FULL : glBufferData(GL_ARRAY_BUFFER, MEM, null, GL_DYNAMIC); glBufferSubData(GL_ARRAY_BUFFER, 0, VI._vtx_queued*_vtx_size, _data ); break;
  683. case GL_LOCK_SUB_RESET_PART_FROM: glBufferData(GL_ARRAY_BUFFER, VI._vtx_queued*_vtx_size, _data, GL_DYNAMIC); break;
  684. case GL_LOCK_SUB_RESET_FULL_FROM: glBufferData(GL_ARRAY_BUFFER, MEM, _data, GL_DYNAMIC); break;
  685. case GL_LOCK_SUB_RING : {UInt offset=VI._vtx_drawing*_vtx_size; glBufferSubData(GL_ARRAY_BUFFER, offset, VI._vtx_queued*_vtx_size, _data+offset);} break;
  686. case GL_LOCK_SUB_RING_RESET : if(_lock_mode==LOCK_WRITE)glBufferData(GL_ARRAY_BUFFER, MEM, null, GL_DYNAMIC); {UInt offset=VI._vtx_drawing*_vtx_size; glBufferSubData(GL_ARRAY_BUFFER, offset, VI._vtx_queued*_vtx_size, _data+offset);} break;
  687. case GL_LOCK_SUB_RING_RESET_FROM: if(_lock_mode==LOCK_WRITE)glBufferData(GL_ARRAY_BUFFER, MEM, _data, GL_DYNAMIC);else {UInt offset=VI._vtx_drawing*_vtx_size; glBufferSubData(GL_ARRAY_BUFFER, offset, VI._vtx_queued*_vtx_size, _data+offset);} break;
  688. }
  689. //glFlush(); no need to flush because it meant to be called only on the main thread for VI
  690. #endif
  691. _lock_mode =LOCK_NONE;
  692. _lock_count=0;
  693. }
  694. Byte* VtxBuf::lock(LOCK_MODE lock)
  695. {
  696. if(lock && _buf)
  697. {
  698. SyncLocker locker(D._lock);
  699. if(!_lock_mode) // first lock
  700. {
  701. #if DX9
  702. Ptr data=null; _buf->Lock(0, 0, &data, (lock==LOCK_WRITE) ? D3DLOCK_DISCARD : (lock==LOCK_APPEND) ? D3DLOCK_NOOVERWRITE : (lock==LOCK_READ) ? D3DLOCK_READONLY : 0);
  703. T._data=(Byte*)data;
  704. #elif DX11
  705. if(_dynamic)
  706. {
  707. if(lock==LOCK_WRITE || lock==LOCK_APPEND)
  708. {
  709. D3D11_MAPPED_SUBRESOURCE map;
  710. if(OK(D3DC->Map(_buf, 0, (lock==LOCK_WRITE) ? D3D11_MAP_WRITE_DISCARD : D3D11_MAP_WRITE_NO_OVERWRITE, 0, &map)))_data=(Byte*)map.pData;
  711. }else
  712. {
  713. // get from GPU
  714. D3D11_BUFFER_DESC desc;
  715. desc.ByteWidth =_vtx_num*_vtx_size;
  716. desc.Usage =D3D11_USAGE_STAGING;
  717. desc.CPUAccessFlags =D3D11_CPU_ACCESS_READ;
  718. desc.BindFlags =0;
  719. desc.MiscFlags =0;
  720. desc.StructureByteStride=0;
  721. ID3D11Buffer *temp=null; if(OK(D3D->CreateBuffer(&desc, null, &temp)))
  722. {
  723. D3DC->CopyResource(temp, _buf);
  724. D3D11_MAPPED_SUBRESOURCE map; if(OK(D3DC->Map(temp, 0, D3D11_MAP_READ, 0, &map)))
  725. {
  726. CPtr src=map.pData; if(OK(D3DC->Map(_buf, 0, D3D11_MAP_WRITE_DISCARD, 0, &map)))
  727. {
  728. _data=(Byte*)map.pData;
  729. CopyFast(_data, src, desc.ByteWidth);
  730. }
  731. D3DC->Unmap(temp, 0);
  732. }
  733. RELEASE(temp);
  734. }
  735. }
  736. }else
  737. {
  738. if(lock==LOCK_WRITE || lock==LOCK_APPEND)Alloc(_data, _vtx_size*_vtx_num);else
  739. {
  740. // get from GPU
  741. D3D11_BUFFER_DESC desc;
  742. desc.ByteWidth =_vtx_size*_vtx_num;
  743. desc.Usage =D3D11_USAGE_STAGING;
  744. desc.CPUAccessFlags=D3D11_CPU_ACCESS_READ;
  745. desc.BindFlags =0;
  746. desc.MiscFlags =0;
  747. desc.StructureByteStride=0;
  748. ID3D11Buffer *temp=null; if(OK(D3D->CreateBuffer(&desc, null, &temp)))
  749. {
  750. D3DC->CopyResource(temp, _buf);
  751. D3D11_MAPPED_SUBRESOURCE map; if(OK(D3DC->Map(temp, 0, D3D11_MAP_READ, 0, &map)))
  752. {
  753. CopyFast(Alloc(_data, desc.ByteWidth), map.pData, desc.ByteWidth);
  754. D3DC->Unmap(temp, 0);
  755. }
  756. RELEASE(temp);
  757. }
  758. }
  759. }
  760. #elif GL
  761. if(IsMap(_dynamic))
  762. {
  763. glBindBuffer (GL_ARRAY_BUFFER, _buf);
  764. _data=(Byte*)glMapBufferRange(GL_ARRAY_BUFFER, 0, _vtx_size*_vtx_num, (lock==LOCK_WRITE) ? GL_MAP_WRITE_BIT|GL_MAP_INVALIDATE_BUFFER_BIT : (lock==LOCK_APPEND) ? GL_MAP_WRITE_BIT : (lock==LOCK_READ) ? GL_MAP_READ_BIT : GL_MAP_READ_BIT|GL_MAP_WRITE_BIT);
  765. }else
  766. {
  767. #if GL_ES
  768. // data is already allocated and ready to use
  769. #else
  770. if(!_data)Alloc(_data, CeilGL(_vtx_size*_vtx_num));
  771. if(lock!=LOCK_WRITE && lock!=LOCK_APPEND) // read
  772. {
  773. glBindBuffer (GL_ARRAY_BUFFER, _buf);
  774. glGetBufferSubData(GL_ARRAY_BUFFER, 0, _vtx_size*_vtx_num, _data);
  775. }
  776. #endif
  777. }
  778. #endif
  779. if(_data)
  780. {
  781. T._lock_mode =lock;
  782. T._lock_count=1;
  783. return _data;
  784. }
  785. }else
  786. if(CompatibleLock(_lock_mode, lock)){_lock_count++; return _data;} // there was already a lock, just increase the counter and return success
  787. }
  788. return null;
  789. }
  790. Ptr IndBuf::lock(LOCK_MODE lock)
  791. {
  792. if(lock && _buf)
  793. {
  794. SyncLocker locker(D._lock);
  795. if(!_lock_mode) // first lock
  796. {
  797. #if DX9
  798. Ptr data=null; _buf->Lock(0, 0, &data, (lock==LOCK_WRITE) ? D3DLOCK_DISCARD : (lock==LOCK_APPEND) ? D3DLOCK_NOOVERWRITE : (lock==LOCK_READ) ? D3DLOCK_READONLY : 0);
  799. T._data=(Byte*)data;
  800. #elif DX11
  801. if(_dynamic)
  802. {
  803. if(lock==LOCK_WRITE || lock==LOCK_APPEND)
  804. {
  805. D3D11_MAPPED_SUBRESOURCE map;
  806. if(OK(D3DC->Map(_buf, 0, (lock==LOCK_WRITE) ? D3D11_MAP_WRITE_DISCARD : D3D11_MAP_WRITE_NO_OVERWRITE, 0, &map)))_data=(Byte*)map.pData;
  807. }else
  808. {
  809. // get from GPU
  810. D3D11_BUFFER_DESC desc;
  811. desc.ByteWidth =_ind_num*(bit16() ? 2 : 4);
  812. desc.Usage =D3D11_USAGE_STAGING;
  813. desc.CPUAccessFlags =D3D11_CPU_ACCESS_READ;
  814. desc.BindFlags =0;
  815. desc.MiscFlags =0;
  816. desc.StructureByteStride=0;
  817. ID3D11Buffer *temp=null; if(OK(D3D->CreateBuffer(&desc, null, &temp)))
  818. {
  819. D3DC->CopyResource(temp, _buf);
  820. D3D11_MAPPED_SUBRESOURCE map; if(OK(D3DC->Map(temp, 0, D3D11_MAP_READ, 0, &map)))
  821. {
  822. CPtr src=map.pData; if(OK(D3DC->Map(_buf, 0, D3D11_MAP_WRITE_DISCARD, 0, &map)))
  823. {
  824. _data=(Byte*)map.pData;
  825. CopyFast(_data, src, desc.ByteWidth);
  826. }
  827. D3DC->Unmap(temp, 0);
  828. }
  829. RELEASE(temp);
  830. }
  831. }
  832. }else
  833. {
  834. if(lock==LOCK_WRITE || lock==LOCK_APPEND)Alloc(_data, _ind_num*(bit16() ? 2 : 4));else
  835. {
  836. // get from GPU
  837. D3D11_BUFFER_DESC desc;
  838. desc.ByteWidth =_ind_num*(bit16() ? 2 : 4);
  839. desc.Usage =D3D11_USAGE_STAGING;
  840. desc.CPUAccessFlags =D3D11_CPU_ACCESS_READ;
  841. desc.BindFlags =0;
  842. desc.MiscFlags =0;
  843. desc.StructureByteStride=0;
  844. ID3D11Buffer *temp=null; if(OK(D3D->CreateBuffer(&desc, null, &temp)))
  845. {
  846. D3DC->CopyResource(temp, _buf);
  847. D3D11_MAPPED_SUBRESOURCE map; if(OK(D3DC->Map(temp, 0, D3D11_MAP_READ, 0, &map)))
  848. {
  849. CopyFast(Alloc(_data, desc.ByteWidth), map.pData, desc.ByteWidth);
  850. D3DC->Unmap(temp, 0);
  851. }
  852. RELEASE(temp);
  853. }
  854. }
  855. }
  856. #elif GL
  857. if(IsMap(_dynamic))
  858. {
  859. BindIndexBuffer(_buf);
  860. _data=(Byte*)glMapBufferRange(GL_ELEMENT_ARRAY_BUFFER, 0, _ind_num*(bit16() ? 2 : 4), (lock==LOCK_WRITE) ? GL_MAP_WRITE_BIT|GL_MAP_INVALIDATE_BUFFER_BIT : (lock==LOCK_APPEND) ? GL_MAP_WRITE_BIT : (lock==LOCK_READ) ? GL_MAP_READ_BIT : GL_MAP_READ_BIT|GL_MAP_WRITE_BIT);
  861. }else
  862. {
  863. #if GL_ES
  864. // data is already allocated and ready to use
  865. #else
  866. if(!_data)Alloc(_data, CeilGL(_ind_num*(bit16() ? 2 : 4)));
  867. if(lock!=LOCK_WRITE && lock!=LOCK_APPEND) // read
  868. {
  869. BindIndexBuffer(_buf);
  870. glGetBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, _ind_num*(bit16() ? 2 : 4), _data);
  871. }
  872. #endif
  873. }
  874. #endif
  875. if(_data)
  876. {
  877. T._lock_mode =lock;
  878. T._lock_count=1;
  879. return _data;
  880. }
  881. }else
  882. if(CompatibleLock(_lock_mode, lock)){_lock_count++; return _data;} // there was already a lock, just increase the counter and return success
  883. }
  884. return null;
  885. }
  886. void VtxBuf::unlock()
  887. {
  888. if(_lock_count>0)
  889. {
  890. SafeSyncLocker lock(D._lock);
  891. if(_lock_count>0)if(!--_lock_count)
  892. {
  893. #if DX9
  894. if(D.created())_buf->Unlock(); _data=null;
  895. #elif DX11
  896. if(_dynamic)
  897. {
  898. if(D3DC)D3DC->Unmap(_buf, 0); _data=null;
  899. }else
  900. {
  901. if(_lock_mode!=LOCK_READ && D3DC)D3DC->UpdateSubresource(_buf, 0, null, _data, 0, 0); Free(_data);
  902. }
  903. #elif GL
  904. if(IsMap(_dynamic))
  905. {
  906. if(D.created())
  907. {
  908. glBindBuffer (GL_ARRAY_BUFFER, _buf);
  909. glUnmapBuffer(GL_ARRAY_BUFFER);
  910. }
  911. _data=null;
  912. }else
  913. {
  914. if(_lock_mode!=LOCK_READ && D.created())
  915. {
  916. glBindBuffer (GL_ARRAY_BUFFER, _buf);
  917. glBufferSubData(GL_ARRAY_BUFFER, 0, _vtx_size*_vtx_num, _data);
  918. glFlush(); // to make sure that the data was initialized, in case it'll be accessed on a secondary thread
  919. }
  920. if(!GL_ES && !_dynamic)Free(_data); // keep data for GLES and dynamic
  921. }
  922. #endif
  923. _lock_mode=LOCK_NONE;
  924. }
  925. }
  926. }
  927. void IndBuf::unlock()
  928. {
  929. if(_lock_count>0)
  930. {
  931. SafeSyncLocker lock(D._lock);
  932. if(_lock_count>0)if(!--_lock_count)
  933. {
  934. #if DX9
  935. if(D.created())_buf->Unlock(); _data=null;
  936. #elif DX11
  937. if(_dynamic)
  938. {
  939. if(D3DC)D3DC->Unmap(_buf, 0); _data=null;
  940. }else
  941. {
  942. if(_lock_mode!=LOCK_READ && D3DC)D3DC->UpdateSubresource(_buf, 0, null, _data, 0, 0); Free(_data);
  943. }
  944. #elif GL
  945. if(IsMap(_dynamic))
  946. {
  947. if(D.created())
  948. {
  949. BindIndexBuffer(_buf);
  950. glUnmapBuffer(GL_ELEMENT_ARRAY_BUFFER);
  951. }
  952. _data=null;
  953. }else
  954. {
  955. if(_lock_mode!=LOCK_READ && D.created())
  956. {
  957. BindIndexBuffer(_buf);
  958. glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, _ind_num*(bit16() ? 2 : 4), _data);
  959. glFlush(); // to make sure that the data was initialized, in case it'll be accessed on a secondary thread
  960. }
  961. if(!GL_ES && !_dynamic)Free(_data); // keep data for GLES and dynamic
  962. }
  963. #endif
  964. _lock_mode=LOCK_NONE;
  965. }
  966. }
  967. }
  968. C Byte* VtxBuf::lockRead()C {return ConstCast(T). lock(LOCK_READ);}
  969. CPtr IndBuf::lockRead()C {return ConstCast(T). lock(LOCK_READ);}
  970. void VtxBuf::unlock ()C { ConstCast(T).unlock();}
  971. void IndBuf::unlock ()C { ConstCast(T).unlock();}
  972. /******************************************************************************/
  973. Bool VtxBuf::setFrom(CPtr data, Int size)
  974. {
  975. if(data)if(Ptr dest=lock(LOCK_WRITE))
  976. {
  977. CopyFast(dest, data, size);
  978. unlock();
  979. return true;
  980. }
  981. return false;
  982. }
  983. Bool IndBuf::setFrom(CPtr data)
  984. {
  985. if(data)if(Ptr dest=lock(LOCK_WRITE))
  986. {
  987. CopyFast(dest, data, memUsage());
  988. unlock();
  989. return true;
  990. }
  991. return false;
  992. }
  993. /******************************************************************************/
  994. #if GL_ES
  995. void VtxBuf::freeOpenGLESData() {if(!_lock_mode && !IsMap(_dynamic))Free(_data);}
  996. void IndBuf::freeOpenGLESData() {if(!_lock_mode && !IsMap(_dynamic))Free(_data);}
  997. #else
  998. void VtxBuf::freeOpenGLESData() {}
  999. void IndBuf::freeOpenGLESData() {}
  1000. #endif
  1001. /******************************************************************************/
  1002. Bool VtxBuf::save(File &f)C
  1003. {
  1004. f.putMulti(Byte(0), _vtx_size, _vtx_num); // version
  1005. if(_vtx_size && _vtx_num)
  1006. {
  1007. if(CPtr data=lockRead()){f.put(data, memUsage()); unlock();}else return false;
  1008. }
  1009. return f.ok();
  1010. }
  1011. Bool VtxBuf::load(File &f)
  1012. {
  1013. switch(f.decUIntV()) // version
  1014. {
  1015. case 0:
  1016. {
  1017. Int vtx_size, vtx_num; f.getMulti(vtx_size, vtx_num); if(f.ok())
  1018. {
  1019. Memt<Byte> temp; if(vtx_size>0 && vtx_num>0 && !temp.setNum(vtx_size*vtx_num).loadRawDataFast(f))goto error;
  1020. return createNum(vtx_size, vtx_num, false, temp.dataNull());
  1021. }
  1022. }break;
  1023. }
  1024. error:
  1025. del(); return false;
  1026. }
  1027. /******************************************************************************/
  1028. Bool IndBuf::save(File &f)C
  1029. {
  1030. f.putMulti(Byte(0), _bit16, _ind_num); // version
  1031. if(_ind_num)
  1032. {
  1033. if(CPtr data=lockRead()){f.put(data, memUsage()); unlock();}else return false;
  1034. }
  1035. return f.ok();
  1036. }
  1037. Bool IndBuf::load(File &f)
  1038. {
  1039. switch(f.decUIntV()) // version
  1040. {
  1041. case 0:
  1042. {
  1043. Bool bit16; Int ind_num; f.getMulti(bit16, ind_num); if(f.ok())
  1044. {
  1045. Memt<Byte> temp; if(ind_num>0 && !temp.setNum(ind_num*(bit16 ? 2 : 4)).loadRawDataFast(f))goto error;
  1046. return create(ind_num, bit16, false, temp.dataNull());
  1047. }
  1048. }break;
  1049. }
  1050. error:
  1051. del(); return false;
  1052. }
  1053. /******************************************************************************/
  1054. // INDEX BUFFER
  1055. /******************************************************************************/
  1056. IndBuf& IndBuf::setTri(Int i, Int v0, Int v1, Int v2)
  1057. {
  1058. if(_data)
  1059. {
  1060. i*=3; // index number
  1061. if(InRange(i+2, _ind_num))
  1062. {
  1063. if(bit16()){U16 *t=((U16*)_data)+i; t[0]=v0; t[1]=v1; t[2]=v2;}
  1064. else {U32 *t=((U32*)_data)+i; t[0]=v0; t[1]=v1; t[2]=v2;}
  1065. }
  1066. }
  1067. return T;
  1068. }
  1069. IndBuf& IndBuf::setQuad(Int i, Int v0, Int v1, Int v2, Int v3)
  1070. {
  1071. if(_data)
  1072. {
  1073. i*=6; // index number
  1074. if(InRange(i+5, _ind_num))
  1075. {
  1076. if(bit16()){U16 *t=((U16*)_data)+i; t[0]=v0; t[1]=v1; t[2]=v3; t[3]=v3; t[4]=v1; t[5]=v2;}
  1077. else {U32 *t=((U32*)_data)+i; t[0]=v0; t[1]=v1; t[2]=v3; t[3]=v3; t[4]=v1; t[5]=v2;}
  1078. }
  1079. }
  1080. return T;
  1081. }
  1082. /******************************************************************************/
  1083. // VERTEX INDEX BUFFER
  1084. /******************************************************************************/
  1085. VtxIndBuf::VtxIndBuf() {}
  1086. void VtxIndBuf::lost()
  1087. {
  1088. unlockVtx(); _vb.del();
  1089. //unlockInd(); _ib.del();
  1090. #if BUFFERS>1
  1091. REPAO(VB).del();
  1092. //REPAO(IB).del();
  1093. #endif
  1094. }
  1095. void VtxIndBuf::reset()
  1096. {
  1097. _mem_max=MEM;
  1098. _vtx_queued=_vtx_drawing=_vtx_drawing_raw=0;
  1099. //_ind_queued=0;
  1100. if(_vb.createRaw(MEM , true))
  1101. //if(_ib.create (MEM/SIZE(U16), true, true)) // divide by size of 1 index
  1102. {
  1103. #if BUFFERS>1
  1104. REPAO(VB).createRaw(MEM , true);
  1105. //REPAO(IB).create (MEM/SIZE(U16), true, true);
  1106. #endif
  1107. clear();
  1108. _vf2D_flat .bind(_vb);
  1109. _vf2D_col .bind(_vb);
  1110. _vf2D_tex .bind(_vb);
  1111. _vf2D_tex_col .bind(_vb);
  1112. _vf2D_tex2 .bind(_vb);
  1113. _vf2D_font .bind(_vb);
  1114. _vf3D_flat .bind(_vb);
  1115. _vf3D_col .bind(_vb);
  1116. _vf3D_tex .bind(_vb);
  1117. _vf3D_tex_col .bind(_vb);
  1118. _vf3D_bilb .bind(_vb);
  1119. _vf3D_bilb_anim.bind(_vb);
  1120. _vf3D_laser .bind(_vb);
  1121. _vf3D_cloth .bind(_vb);
  1122. _vf3D_simple .bind(_vb);
  1123. _vf3D_standard .bind(_vb);
  1124. _vf3D_full .bind(_vb);
  1125. return;
  1126. }
  1127. Exit("Can't create Vertex/Index Buffer");
  1128. }
  1129. void VtxIndBuf::del()
  1130. {
  1131. lost();
  1132. _vf2D_flat .del();
  1133. _vf2D_col .del();
  1134. _vf2D_tex .del();
  1135. _vf2D_tex_col .del();
  1136. _vf2D_tex2 .del();
  1137. _vf2D_font .del();
  1138. _vf3D_flat .del();
  1139. _vf3D_col .del();
  1140. _vf3D_tex .del();
  1141. _vf3D_tex_col .del();
  1142. _vf3D_bilb .del();
  1143. _vf3D_bilb_anim.del();
  1144. _vf3D_laser .del();
  1145. _vf3D_cloth .del();
  1146. _vf3D_simple .del();
  1147. _vf3D_standard .del();
  1148. _vf3D_full .del();
  1149. }
  1150. void VtxIndBuf::create()
  1151. {
  1152. #pragma warning(push)
  1153. #pragma warning(disable:4838)
  1154. #if DX9
  1155. {
  1156. D3DVERTEXELEMENT9 ve[]={
  1157. {0, OFFSET(Vtx2DFlat, pos), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1158. D3DDECL_END()}; _vf2D_flat.create(ve);
  1159. }
  1160. {
  1161. D3DVERTEXELEMENT9 ve[]={
  1162. {0, OFFSET(Vtx2DCol, pos ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1163. {0, OFFSET(Vtx2DCol, color), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1164. D3DDECL_END()}; _vf2D_col.create(ve);
  1165. }
  1166. {
  1167. D3DVERTEXELEMENT9 ve[]={
  1168. {0, OFFSET(Vtx2DTex, pos), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1169. {0, OFFSET(Vtx2DTex, tex), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1170. D3DDECL_END()}; _vf2D_tex.create(ve);
  1171. }
  1172. {
  1173. D3DVERTEXELEMENT9 ve[]={
  1174. {0, OFFSET(Vtx2DTexCol, pos ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1175. {0, OFFSET(Vtx2DTexCol, tex ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1176. {0, OFFSET(Vtx2DTexCol, color), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1177. D3DDECL_END()}; _vf2D_tex_col.create(ve);
  1178. }
  1179. {
  1180. D3DVERTEXELEMENT9 ve[]={
  1181. {0, OFFSET(Vtx2DTex2, pos ), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1182. {0, OFFSET(Vtx2DTex2, tex[0]), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1183. {0, OFFSET(Vtx2DTex2, tex[1]), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
  1184. D3DDECL_END()}; _vf2D_tex2.create(ve);
  1185. }
  1186. {
  1187. D3DVERTEXELEMENT9 ve[]={
  1188. {0, OFFSET(Vtx2DFont, pos ), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1189. {0, OFFSET(Vtx2DFont, tex ), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1190. {0, OFFSET(Vtx2DFont, shade), D3DDECLTYPE_FLOAT1, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_PSIZE , 0},
  1191. D3DDECL_END()}; _vf2D_font.create(ve);
  1192. }
  1193. {
  1194. D3DVERTEXELEMENT9 ve[]={
  1195. {0, OFFSET(Vtx3DFlat, pos), D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1196. D3DDECL_END()}; _vf3D_flat.create(ve);
  1197. }
  1198. {
  1199. D3DVERTEXELEMENT9 ve[]={
  1200. {0, OFFSET(Vtx3DCol, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1201. {0, OFFSET(Vtx3DCol, color), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1202. D3DDECL_END()}; _vf3D_col.create(ve);
  1203. }
  1204. {
  1205. D3DVERTEXELEMENT9 ve[]={
  1206. {0, OFFSET(Vtx3DTex, pos), D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1207. {0, OFFSET(Vtx3DTex, tex), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1208. D3DDECL_END()}; _vf3D_tex.create(ve);
  1209. }
  1210. {
  1211. D3DVERTEXELEMENT9 ve[]={
  1212. {0, OFFSET(Vtx3DTexCol, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1213. {0, OFFSET(Vtx3DTexCol, tex ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1214. {0, OFFSET(Vtx3DTexCol, color), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1215. D3DDECL_END()}; _vf3D_tex_col.create(ve);
  1216. }
  1217. {
  1218. D3DVERTEXELEMENT9 ve[]={
  1219. {0, OFFSET(Vtx3DBilb, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1220. #if GPU_HALF_SUPPORTED
  1221. {0, OFFSET(Vtx3DBilb, vel_angle), D3DDECLTYPE_FLOAT16_4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT , 0},
  1222. #else
  1223. {0, OFFSET(Vtx3DBilb, vel_angle), D3DDECLTYPE_FLOAT4 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT , 0},
  1224. #endif
  1225. {0, OFFSET(Vtx3DBilb, tex ), D3DDECLTYPE_UBYTE4N , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1226. {0, OFFSET(Vtx3DBilb, size ), D3DDECLTYPE_FLOAT1 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_PSIZE , 0},
  1227. {0, OFFSET(Vtx3DBilb, color ), D3DDECLTYPE_UBYTE4N , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1228. D3DDECL_END()}; _vf3D_bilb.create(ve);
  1229. }
  1230. {
  1231. D3DVERTEXELEMENT9 ve[]={
  1232. {0, OFFSET(Vtx3DBilbAnim, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1233. #if GPU_HALF_SUPPORTED
  1234. {0, OFFSET(Vtx3DBilbAnim, vel_angle), D3DDECLTYPE_FLOAT16_4, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT , 0},
  1235. #else
  1236. {0, OFFSET(Vtx3DBilbAnim, vel_angle), D3DDECLTYPE_FLOAT4 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT , 0},
  1237. #endif
  1238. {0, OFFSET(Vtx3DBilbAnim, tex ), D3DDECLTYPE_UBYTE4N , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1239. {0, OFFSET(Vtx3DBilbAnim, size ), D3DDECLTYPE_FLOAT1 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_PSIZE , 0},
  1240. {0, OFFSET(Vtx3DBilbAnim, color ), D3DDECLTYPE_UBYTE4N , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1241. {0, OFFSET(Vtx3DBilbAnim, frame ), D3DDECLTYPE_FLOAT1 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 1},
  1242. D3DDECL_END()}; _vf3D_bilb_anim.create(ve);
  1243. }
  1244. {
  1245. D3DVERTEXELEMENT9 ve[]={
  1246. {0, OFFSET(Vtx3DLaser, pos), D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1247. {0, OFFSET(Vtx3DLaser, nrm), D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL , 0},
  1248. D3DDECL_END()}; _vf3D_laser.create(ve);
  1249. }
  1250. {
  1251. D3DVERTEXELEMENT9 ve[]={
  1252. {0, OFFSET(Cloth::Vtx, pos), D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1253. {0, OFFSET(Cloth::Vtx, nrm), D3DDECLTYPE_FLOAT3, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL , 0},
  1254. {0, OFFSET(Cloth::Vtx, tex), D3DDECLTYPE_FLOAT2, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1255. D3DDECL_END()}; _vf3D_cloth.create(ve);
  1256. }
  1257. {
  1258. D3DVERTEXELEMENT9 ve[]={
  1259. {0, OFFSET(Vtx3DSimple, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1260. {0, OFFSET(Vtx3DSimple, nrm ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL , 0},
  1261. {0, OFFSET(Vtx3DSimple, tex ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1262. {0, OFFSET(Vtx3DSimple, color), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1263. D3DDECL_END()}; _vf3D_simple.create(ve);
  1264. }
  1265. {
  1266. D3DVERTEXELEMENT9 ve[]={
  1267. {0, OFFSET(Vtx3DStandard, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION, 0},
  1268. {0, OFFSET(Vtx3DStandard, nrm ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL , 0},
  1269. {0, OFFSET(Vtx3DStandard, tan ), D3DDECLTYPE_FLOAT4 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT , 0},
  1270. {0, OFFSET(Vtx3DStandard, tex ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD, 0},
  1271. {0, OFFSET(Vtx3DStandard, color), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1272. D3DDECL_END()}; _vf3D_standard.create(ve);
  1273. }
  1274. {
  1275. D3DVERTEXELEMENT9 ve[]={
  1276. {0, OFFSET(Vtx3DFull, pos ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION , 0},
  1277. {0, OFFSET(Vtx3DFull, hlp ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_POSITION , 1},
  1278. {0, OFFSET(Vtx3DFull, nrm ), D3DDECLTYPE_FLOAT3 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_NORMAL , 0},
  1279. {0, OFFSET(Vtx3DFull, tan ), D3DDECLTYPE_FLOAT4 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TANGENT , 0},
  1280. {0, OFFSET(Vtx3DFull, tex0 ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD , 0},
  1281. {0, OFFSET(Vtx3DFull, tex1 ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD , 1},
  1282. {0, OFFSET(Vtx3DFull, tex2 ), D3DDECLTYPE_FLOAT2 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_TEXCOORD , 2},
  1283. {0, OFFSET(Vtx3DFull, color ), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 1},
  1284. {0, OFFSET(Vtx3DFull, material), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_COLOR , 0},
  1285. {0, OFFSET(Vtx3DFull, matrix ), D3DDECLTYPE_UBYTE4 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_BLENDINDICES, 0},
  1286. {0, OFFSET(Vtx3DFull, blend ), D3DDECLTYPE_UBYTE4N, D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_BLENDWEIGHT , 0},
  1287. {0, OFFSET(Vtx3DFull, size ), D3DDECLTYPE_FLOAT1 , D3DDECLMETHOD_DEFAULT, D3DDECLUSAGE_PSIZE , 0},
  1288. D3DDECL_END()}; _vf3D_full.create(ve);
  1289. }
  1290. #elif DX11
  1291. {
  1292. D3D11_INPUT_ELEMENT_DESC ve[]=
  1293. {
  1294. {"POSITION" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DFlat, pos), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1295. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1296. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1297. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1298. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1299. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1300. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1301. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1302. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1303. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1304. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1305. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1306. };
  1307. _vf2D_flat.create(ve, Elms(ve));
  1308. }
  1309. {
  1310. D3D11_INPUT_ELEMENT_DESC ve[]=
  1311. {
  1312. {"POSITION" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DCol, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1313. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1314. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1315. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1316. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1317. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1318. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1319. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1320. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1321. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1322. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1323. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx2DCol, color), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1324. };
  1325. _vf2D_col.create(ve, Elms(ve));
  1326. }
  1327. {
  1328. D3D11_INPUT_ELEMENT_DESC ve[]=
  1329. {
  1330. {"POSITION" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTex, pos), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1331. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1332. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1333. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1334. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTex, tex), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1335. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1336. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1337. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1338. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1339. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1340. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1341. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1342. };
  1343. _vf2D_tex.create(ve, Elms(ve));
  1344. }
  1345. {
  1346. D3D11_INPUT_ELEMENT_DESC ve[]=
  1347. {
  1348. {"POSITION" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTexCol, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1349. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1350. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1351. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1352. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTexCol, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1353. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1354. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1355. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1356. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1357. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1358. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1359. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx2DTexCol, color), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1360. };
  1361. _vf2D_tex_col.create(ve, Elms(ve));
  1362. }
  1363. {
  1364. D3D11_INPUT_ELEMENT_DESC ve[]=
  1365. {
  1366. {"POSITION" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTex2, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1367. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1368. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1369. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1370. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTex2, tex[0]), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1371. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DTex2, tex[1]), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1372. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1373. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1374. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1375. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1376. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1377. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1378. };
  1379. _vf2D_tex2.create(ve, Elms(ve));
  1380. }
  1381. {
  1382. D3D11_INPUT_ELEMENT_DESC ve[]=
  1383. {
  1384. {"POSITION" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DFont, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1385. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1386. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1387. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1388. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx2DFont, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1389. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1390. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1391. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, OFFSET(Vtx2DFont, shade), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1392. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1393. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1394. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1395. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1396. };
  1397. _vf2D_font.create(ve, Elms(ve));
  1398. }
  1399. {
  1400. D3D11_INPUT_ELEMENT_DESC ve[]=
  1401. {
  1402. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DFlat, pos), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1403. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1404. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1405. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1406. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1407. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1408. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1409. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1410. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1411. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1412. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1413. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1414. };
  1415. _vf3D_flat.create(ve, Elms(ve));
  1416. }
  1417. {
  1418. D3D11_INPUT_ELEMENT_DESC ve[]=
  1419. {
  1420. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DCol, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1421. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1422. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1423. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1424. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1425. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1426. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1427. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1428. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1429. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1430. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1431. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DCol, color), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1432. };
  1433. _vf3D_col.create(ve, Elms(ve));
  1434. }
  1435. {
  1436. D3D11_INPUT_ELEMENT_DESC ve[]=
  1437. {
  1438. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DTex, pos), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1439. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1440. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1441. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1442. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DTex, tex), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1443. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1444. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1445. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1446. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1447. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1448. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1449. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1450. };
  1451. _vf3D_tex.create(ve, Elms(ve));
  1452. }
  1453. {
  1454. D3D11_INPUT_ELEMENT_DESC ve[]=
  1455. {
  1456. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DTexCol, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1457. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1458. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1459. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1460. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DTexCol, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1461. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1462. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1463. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1464. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1465. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1466. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1467. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DTexCol, color), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1468. };
  1469. _vf3D_tex_col.create(ve, Elms(ve));
  1470. }
  1471. {
  1472. D3D11_INPUT_ELEMENT_DESC ve[]=
  1473. {
  1474. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DBilb, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1475. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1476. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1477. #if GPU_HALF_SUPPORTED
  1478. {"TANGENT" , 0, DXGI_FORMAT_R16G16B16A16_FLOAT, 0, OFFSET(Vtx3DBilb, vel_angle), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1479. #else
  1480. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, OFFSET(Vtx3DBilb, vel_angle), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1481. #endif
  1482. {"TEXCOORD" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DBilb, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1483. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1484. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1485. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, OFFSET(Vtx3DBilb, size ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1486. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1487. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1488. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1489. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DBilb, color ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1490. };
  1491. _vf3D_bilb.create(ve, Elms(ve));
  1492. }
  1493. {
  1494. D3D11_INPUT_ELEMENT_DESC ve[]=
  1495. {
  1496. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DBilbAnim, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1497. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1498. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1499. #if GPU_HALF_SUPPORTED
  1500. {"TANGENT" , 0, DXGI_FORMAT_R16G16B16A16_FLOAT, 0, OFFSET(Vtx3DBilbAnim, vel_angle), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1501. #else
  1502. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, OFFSET(Vtx3DBilbAnim, vel_angle), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1503. #endif
  1504. {"TEXCOORD" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DBilbAnim, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1505. {"TEXCOORD" , 1, DXGI_FORMAT_R32_FLOAT , 0, OFFSET(Vtx3DBilbAnim, frame ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1506. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1507. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, OFFSET(Vtx3DBilbAnim, size ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1508. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1509. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1510. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1511. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DBilbAnim, color ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1512. };
  1513. _vf3D_bilb_anim.create(ve, Elms(ve));
  1514. }
  1515. {
  1516. D3D11_INPUT_ELEMENT_DESC ve[]=
  1517. {
  1518. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DLaser, pos), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1519. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1520. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DLaser, nrm), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1521. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1522. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1523. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1524. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1525. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1526. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1527. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1528. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1529. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1530. };
  1531. _vf3D_laser.create(ve, Elms(ve));
  1532. }
  1533. {
  1534. D3D11_INPUT_ELEMENT_DESC ve[]=
  1535. {
  1536. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Cloth::Vtx, pos), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1537. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1538. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Cloth::Vtx, nrm), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1539. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1540. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Cloth::Vtx, tex), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1541. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1542. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1543. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1544. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1545. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1546. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1547. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1548. };
  1549. _vf3D_cloth.create(ve, Elms(ve));
  1550. }
  1551. {
  1552. D3D11_INPUT_ELEMENT_DESC ve[]=
  1553. {
  1554. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DSimple, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1555. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1556. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DSimple, nrm ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1557. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1558. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DSimple, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1559. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1560. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1561. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1562. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1563. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1564. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1565. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DSimple, color), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1566. };
  1567. _vf3D_simple.create(ve, Elms(ve));
  1568. }
  1569. {
  1570. D3D11_INPUT_ELEMENT_DESC ve[]=
  1571. {
  1572. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DStandard, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1573. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1574. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DStandard, nrm ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1575. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, OFFSET(Vtx3DStandard, tan ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1576. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DStandard, tex ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1577. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1578. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1579. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1580. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1581. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1582. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0},
  1583. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DStandard, color), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1584. };
  1585. _vf3D_standard.create(ve, Elms(ve));
  1586. }
  1587. {
  1588. D3D11_INPUT_ELEMENT_DESC ve[]=
  1589. {
  1590. {"POSITION" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DFull, pos ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1591. {"POSITION" , 1, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DFull, hlp ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1592. {"NORMAL" , 0, DXGI_FORMAT_R32G32B32_FLOAT , 0, OFFSET(Vtx3DFull, nrm ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1593. {"TANGENT" , 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, OFFSET(Vtx3DFull, tan ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1594. {"TEXCOORD" , 0, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DFull, tex0 ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1595. {"TEXCOORD" , 1, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DFull, tex1 ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1596. {"TEXCOORD" , 2, DXGI_FORMAT_R32G32_FLOAT , 0, OFFSET(Vtx3DFull, tex2 ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1597. {"PSIZE" , 0, DXGI_FORMAT_R32_FLOAT , 0, OFFSET(Vtx3DFull, size ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1598. {"BLENDINDICES", 0, DXGI_FORMAT_R8G8B8A8_UINT , 0, OFFSET(Vtx3DFull, matrix ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1599. {"BLENDWEIGHT" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DFull, blend ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1600. {"COLOR" , 0, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DFull, material), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1601. {"COLOR" , 1, DXGI_FORMAT_R8G8B8A8_UNORM , 0, OFFSET(Vtx3DFull, color ), D3D11_INPUT_PER_VERTEX_DATA, 0},
  1602. };
  1603. _vf3D_full.create(ve, Elms(ve));
  1604. }
  1605. #elif GL
  1606. MemtN<VtxFormatGL::Elm, 32> ve;
  1607. {
  1608. ve.New().set(GL_VTX_POS, 2, GL_FLOAT, false, OFFSET(Vtx2DFlat, pos));
  1609. _vf2D_flat.create(ve); ve.clear();
  1610. }
  1611. {
  1612. ve.New().set(GL_VTX_POS , 2, GL_FLOAT , false, OFFSET(Vtx2DCol, pos ));
  1613. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx2DCol, color));
  1614. _vf2D_col.create(ve); ve.clear();
  1615. }
  1616. {
  1617. ve.New().set(GL_VTX_POS , 2, GL_FLOAT, false, OFFSET(Vtx2DTex, pos));
  1618. ve.New().set(GL_VTX_TEX0, 2, GL_FLOAT, false, OFFSET(Vtx2DTex, tex));
  1619. _vf2D_tex.create(ve); ve.clear();
  1620. }
  1621. {
  1622. ve.New().set(GL_VTX_POS , 2, GL_FLOAT , false, OFFSET(Vtx2DTexCol, pos ));
  1623. ve.New().set(GL_VTX_TEX0 , 2, GL_FLOAT , false, OFFSET(Vtx2DTexCol, tex ));
  1624. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx2DTexCol, color));
  1625. _vf2D_tex_col.create(ve); ve.clear();
  1626. }
  1627. {
  1628. ve.New().set(GL_VTX_POS , 2, GL_FLOAT, false, OFFSET(Vtx2DTex2, pos ));
  1629. ve.New().set(GL_VTX_TEX0, 2, GL_FLOAT, false, OFFSET(Vtx2DTex2, tex[0]));
  1630. ve.New().set(GL_VTX_TEX1, 2, GL_FLOAT, false, OFFSET(Vtx2DTex2, tex[1]));
  1631. _vf2D_tex2.create(ve); ve.clear();
  1632. }
  1633. {
  1634. ve.New().set(GL_VTX_POS , 2, GL_FLOAT, false, OFFSET(Vtx2DFont, pos ));
  1635. ve.New().set(GL_VTX_TEX0, 2, GL_FLOAT, false, OFFSET(Vtx2DFont, tex ));
  1636. ve.New().set(GL_VTX_SIZE, 1, GL_FLOAT, false, OFFSET(Vtx2DFont, shade));
  1637. _vf2D_font.create(ve); ve.clear();
  1638. }
  1639. {
  1640. ve.New().set(GL_VTX_POS, 3, GL_FLOAT, false, OFFSET(Vtx3DFlat, pos));
  1641. _vf3D_flat.create(ve); ve.clear();
  1642. }
  1643. {
  1644. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DCol, pos ));
  1645. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DCol, color));
  1646. _vf3D_col.create(ve); ve.clear();
  1647. }
  1648. {
  1649. ve.New().set(GL_VTX_POS , 3, GL_FLOAT, false, OFFSET(Vtx3DTex, pos));
  1650. ve.New().set(GL_VTX_TEX0, 2, GL_FLOAT, false, OFFSET(Vtx3DTex, tex));
  1651. _vf3D_tex.create(ve); ve.clear();
  1652. }
  1653. {
  1654. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DTexCol, pos ));
  1655. ve.New().set(GL_VTX_TEX0 , 2, GL_FLOAT , false, OFFSET(Vtx3DTexCol, tex ));
  1656. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DTexCol, color));
  1657. _vf3D_tex_col.create(ve); ve.clear();
  1658. }
  1659. {
  1660. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DBilb, pos ));
  1661. #if GPU_HALF_SUPPORTED
  1662. ve.New().set(GL_VTX_TAN , 4, GL_HALF_FLOAT , false, OFFSET(Vtx3DBilb, vel_angle));
  1663. #else
  1664. ve.New().set(GL_VTX_TAN , 4, GL_FLOAT , false, OFFSET(Vtx3DBilb, vel_angle));
  1665. #endif
  1666. ve.New().set(GL_VTX_TEX0 , 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DBilb, tex ));
  1667. ve.New().set(GL_VTX_SIZE , 1, GL_FLOAT , false, OFFSET(Vtx3DBilb, size ));
  1668. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DBilb, color ));
  1669. _vf3D_bilb.create(ve); ve.clear();
  1670. }
  1671. {
  1672. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DBilbAnim, pos ));
  1673. #if GPU_HALF_SUPPORTED
  1674. ve.New().set(GL_VTX_TAN , 4, GL_HALF_FLOAT , false, OFFSET(Vtx3DBilbAnim, vel_angle));
  1675. #else
  1676. ve.New().set(GL_VTX_TAN , 4, GL_FLOAT , false, OFFSET(Vtx3DBilbAnim, vel_angle));
  1677. #endif
  1678. ve.New().set(GL_VTX_TEX0 , 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DBilbAnim, tex ));
  1679. ve.New().set(GL_VTX_SIZE , 1, GL_FLOAT , false, OFFSET(Vtx3DBilbAnim, size ));
  1680. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DBilbAnim, color ));
  1681. ve.New().set(GL_VTX_TEX1 , 1, GL_FLOAT , false, OFFSET(Vtx3DBilbAnim, frame ));
  1682. _vf3D_bilb_anim.create(ve); ve.clear();
  1683. }
  1684. {
  1685. ve.New().set(GL_VTX_POS, 3, GL_FLOAT, false, OFFSET(Vtx3DLaser, pos));
  1686. ve.New().set(GL_VTX_NRM, 3, GL_FLOAT, false, OFFSET(Vtx3DLaser, nrm));
  1687. _vf3D_laser.create(ve); ve.clear();
  1688. }
  1689. {
  1690. ve.New().set(GL_VTX_POS , 3, GL_FLOAT, false, OFFSET(Cloth::Vtx, pos));
  1691. ve.New().set(GL_VTX_NRM , 3, GL_FLOAT, false, OFFSET(Cloth::Vtx, nrm));
  1692. ve.New().set(GL_VTX_TEX0, 2, GL_FLOAT, false, OFFSET(Cloth::Vtx, tex));
  1693. _vf3D_cloth.create(ve); ve.clear();
  1694. }
  1695. {
  1696. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DSimple, pos ));
  1697. ve.New().set(GL_VTX_NRM , 3, GL_FLOAT , false, OFFSET(Vtx3DSimple, nrm ));
  1698. ve.New().set(GL_VTX_TEX0 , 2, GL_FLOAT , false, OFFSET(Vtx3DSimple, tex ));
  1699. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DSimple, color));
  1700. _vf3D_simple.create(ve); ve.clear();
  1701. }
  1702. {
  1703. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DStandard, pos ));
  1704. ve.New().set(GL_VTX_NRM , 3, GL_FLOAT , false, OFFSET(Vtx3DStandard, nrm ));
  1705. ve.New().set(GL_VTX_TAN , 4, GL_FLOAT , false, OFFSET(Vtx3DStandard, tan ));
  1706. ve.New().set(GL_VTX_TEX0 , 2, GL_FLOAT , false, OFFSET(Vtx3DStandard, tex ));
  1707. ve.New().set(GL_VTX_COLOR, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DStandard, color));
  1708. _vf3D_standard.create(ve); ve.clear();
  1709. }
  1710. {
  1711. ve.New().set(GL_VTX_POS , 3, GL_FLOAT , false, OFFSET(Vtx3DFull, pos ));
  1712. ve.New().set(GL_VTX_HLP , 3, GL_FLOAT , false, OFFSET(Vtx3DFull, hlp ));
  1713. ve.New().set(GL_VTX_NRM , 3, GL_FLOAT , false, OFFSET(Vtx3DFull, nrm ));
  1714. ve.New().set(GL_VTX_TAN , 4, GL_FLOAT , false, OFFSET(Vtx3DFull, tan ));
  1715. ve.New().set(GL_VTX_TEX0 , 2, GL_FLOAT , false, OFFSET(Vtx3DFull, tex0 ));
  1716. ve.New().set(GL_VTX_TEX1 , 2, GL_FLOAT , false, OFFSET(Vtx3DFull, tex1 ));
  1717. ve.New().set(GL_VTX_TEX2 , 2, GL_FLOAT , false, OFFSET(Vtx3DFull, tex2 ));
  1718. ve.New().set(GL_VTX_COLOR , 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DFull, color ));
  1719. ve.New().set(GL_VTX_MATERIAL, 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DFull, material));
  1720. ve.New().set(GL_VTX_BONE , 4, GL_UNSIGNED_BYTE, false, OFFSET(Vtx3DFull, matrix ));
  1721. ve.New().set(GL_VTX_WEIGHT , 4, GL_UNSIGNED_BYTE, true , OFFSET(Vtx3DFull, blend ));
  1722. ve.New().set(GL_VTX_SIZE , 1, GL_FLOAT , false, OFFSET(Vtx3DFull, size ));
  1723. _vf3D_full.create(ve); ve.clear();
  1724. }
  1725. #endif
  1726. #pragma warning(pop)
  1727. reset();
  1728. }
  1729. /******************************************************************************/
  1730. #if BUFFERS<=1
  1731. Bool VtxIndBuf:: lockVtx() {if(!VI._vtx_buf)VI._vtx_buf= VI._vb. lockDynamic(); return VI._vtx_buf!=null; }
  1732. //Bool VtxIndBuf:: lockInd() {if(!VI._ind_buf)VI._ind_buf=(U16*)VI._ib. lockDynamic(); return VI._ind_buf!=null; }
  1733. void VtxIndBuf::unlockVtx() {if( VI._vtx_buf){ VI._vb.unlockDynamic(); VI._vtx_buf =null;}}
  1734. //void VtxIndBuf::unlockInd() {if( VI._ind_buf){ VI._ib.unlockDynamic(); VI._ind_buf =null;}}
  1735. #else
  1736. Bool VtxIndBuf::lockVtx()
  1737. {
  1738. if(!VI._vtx_buf)
  1739. {
  1740. VI_vb++; if(VI_vb>=VB+BUFFERS_USE)VI_vb=VB; // proceed to the next one, and go back to start if reached the end
  1741. VI_vb->_vtx_size=VI._vb._vtx_size; // copy current settings
  1742. VI_vb->_vtx_num =VI._vb._vtx_num ; // copy current settings
  1743. VI ._vtx_buf =VI_vb->lockDynamic();
  1744. VI_vb->set( );
  1745. #if GL
  1746. D .vf (VF); // set VF after VBO on OpenGL
  1747. #endif
  1748. }
  1749. return VI._vtx_buf!=null;
  1750. }
  1751. /*Bool VtxIndBuf::lockInd()
  1752. {
  1753. if(!VI._ind_buf)
  1754. {
  1755. VI_ib++; if(VI_ib>=IB+BUFFERS_USE)VI_ib=IB;
  1756. VI._ind_buf=(U16*)VI_ib->lockDynamic();
  1757. VI_ib->set();
  1758. }
  1759. return VI._ind_buf!=null;
  1760. }*/
  1761. void VtxIndBuf::unlockVtx() {if(VI._vtx_buf){VI_vb->unlockDynamic(); VI._vtx_buf=null;}}
  1762. //void VtxIndBuf::unlockInd() {if(VI._ind_buf){VI_ib->unlockDynamic(); VI._ind_buf=null;}}
  1763. #endif
  1764. /******************************************************************************/
  1765. void VtxIndBuf::setType(VI_TYPE vtx_type, UInt flag)
  1766. {
  1767. Shader *shader;
  1768. VtxFormat *vf;
  1769. switch(VI._vtx_type=vtx_type)
  1770. {
  1771. case VI_2D_FLAT : VI._vb._vtx_size=SIZE(Vtx2DFlat ); shader=Sh.h_Draw2DFlat ; vf=&VI._vf2D_flat ; D.depth(false); D.cull(false); break;
  1772. case VI_2D_COL : VI._vb._vtx_size=SIZE(Vtx2DCol ); shader=Sh.h_Draw2DCol ; vf=&VI._vf2D_col ; D.depth(false); D.cull(false); break;
  1773. case VI_2D_TEX : VI._vb._vtx_size=SIZE(Vtx2DTex ); shader=((flag&VI_SP_COL) ? Sh.h_Draw2DTexC : Sh.h_Draw2DTex) ; vf=&VI._vf2D_tex ; D.depth(false); D.cull(false); break;
  1774. case VI_2D_TEX_COL : VI._vb._vtx_size=SIZE(Vtx2DTexCol ); shader=Sh.h_Draw2DTexCol ; vf=&VI._vf2D_tex_col ; D.depth(false); D.cull(false); break;
  1775. case VI_2D_TEX2 : VI._vb._vtx_size=SIZE(Vtx2DTex2 ); shader=Sh.h_DrawMask ; vf=&VI._vf2D_tex2 ; D.depth(false); D.cull(false); break;
  1776. case VI_2D_FONT : VI._vb._vtx_size=SIZE(Vtx2DFont ); shader=Sh.h_Font ; vf=&VI._vf2D_font ; D.depth(false); D.cull(false); break;
  1777. case VI_3D_FLAT : VI._vb._vtx_size=SIZE(Vtx3DFlat ); shader=Sh.h_Draw3DFlat ; vf=&VI._vf3D_flat ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1778. case VI_3D_COL : VI._vb._vtx_size=SIZE(Vtx3DCol ); shader=Sh.h_Draw3DCol ; vf=&VI._vf3D_col ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1779. case VI_3D_TEX : VI._vb._vtx_size=SIZE(Vtx3DTex ); shader=Sh.h_Draw3DTex [FlagTest(VI._user_flag, VI_ALPHA_TEST)][FlagTest(VI._user_flag, VI_FOG) && Fog.draw]; vf=&VI._vf3D_tex ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1780. case VI_3D_TEX_COL : VI._vb._vtx_size=SIZE(Vtx3DTexCol ); shader=Sh.h_Draw3DTexCol[FlagTest(VI._user_flag, VI_ALPHA_TEST)][FlagTest(VI._user_flag, VI_FOG) && Fog.draw]; vf=&VI._vf3D_tex_col ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1781. case VI_3D_BILB : VI._vb._vtx_size=SIZE(Vtx3DBilb ); shader=Sh.h_Bilb ; vf=&VI._vf3D_bilb ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1782. case VI_3D_BILB_ANIM: VI._vb._vtx_size=SIZE(Vtx3DBilbAnim); shader=null ; vf=&VI._vf3D_bilb_anim; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1783. case VI_3D_LASER : VI._vb._vtx_size=SIZE(Vtx3DLaser ); shader=null ; vf=&VI._vf3D_laser ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1784. case VI_3D_SIMPLE : VI._vb._vtx_size=SIZE(Vtx3DSimple ); shader=Sh.h_Simple ; vf=&VI._vf3D_simple ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1785. case VI_3D_STANDARD : VI._vb._vtx_size=SIZE(Vtx3DStandard); shader=Sh.h_Simple ; vf=&VI._vf3D_standard ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1786. case VI_3D_FULL : VI._vb._vtx_size=SIZE(Vtx3DFull ); shader=null ; vf=&VI._vf3D_full ; D.depth(true ); D.cull(FlagTest(VI._user_flag, VI_CULL)); break;
  1787. default : return;
  1788. }
  1789. #if GL
  1790. #if BUFFERS<=1
  1791. if(D.notShaderModelGLES2())glBindVertexArray(vf->vf->vao); // !! OpenGL requires setting VAO before VB and IB !! calling 'glBindVertexArray' on GLES2 would crash
  1792. #else
  1793. SetDefaultVAO(); // when using multiple buffers we need to set default 'VAO' because we will use 'D.vf' later, for which we need 'VAO' only
  1794. #endif
  1795. #endif
  1796. if(!VI._shader)VI._shader=shader;
  1797. VI._vb._vtx_num=Min(0xFFFF, MEM / VI._vb._vtx_size); // limit to 0xFFFF because of U16 indexing (drawIndexed)
  1798. VI._vtx_drawing= DivCeil(VI._vtx_drawing_raw, VI._vb._vtx_size);
  1799. VI._flag =flag;
  1800. if(VI._quad_ind =FlagTest(flag, VI_QUAD_IND))IndBuf16384Quads.set(); // !! set after 'glBindVertexArray' !!
  1801. if(flag&VI_LINE)
  1802. {
  1803. if(flag&VI_STRIP){VI._prim_type=GPU_API(D3DPT_LINESTRIP, D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP, GL_LINE_STRIP); VI._ind_div=1; VI._ind_sub=1;}
  1804. else {VI._prim_type=GPU_API(D3DPT_LINELIST , D3D11_PRIMITIVE_TOPOLOGY_LINELIST , GL_LINES ); VI._ind_div=2; VI._ind_sub=0;}
  1805. }else
  1806. {
  1807. if(flag&VI_STRIP){VI._prim_type=GPU_API(D3DPT_TRIANGLESTRIP, D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP, GL_TRIANGLE_STRIP); VI._ind_div=1; VI._ind_sub=2;}
  1808. else {VI._prim_type=GPU_API(D3DPT_TRIANGLELIST , D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST , GL_TRIANGLES ); VI._ind_div=3; VI._ind_sub=0;}
  1809. }
  1810. SetVtxNrmMulAdd(false);
  1811. #if BUFFERS<=1
  1812. if(!GL || D.shaderModelGLES2()) // for GL we juse use VAO which already sets VB and VF (because VB's are bound to VAO during 'VI.reset')
  1813. {
  1814. VI._vb.set(); // OpenGL requires setting VB after VAO but before VF, DX10+ requires calling this after setting '_vtx_size'
  1815. //VI._ib.set(); we don't use index buffers here, all possible index buffers are set elsewhere ('IndBuf16384Quads' is above, and custom are in 'flushIndexed')
  1816. D.vf(vf->vf);
  1817. }
  1818. #else
  1819. #if DX9 || DX11
  1820. D.vf(vf->vf);
  1821. #elif GL
  1822. VF=vf->vf; // remember for future use
  1823. #endif
  1824. if(VI._vtx_buf) // if we already have a vtx buffer locked, then we need to adjust it
  1825. {
  1826. VI_vb->_vtx_size=VI._vb._vtx_size; // copy current settings
  1827. VI_vb->_vtx_num =VI._vb._vtx_num ; // copy current settings
  1828. VI_vb->set(); // make sure that it's active (some other vtx buffer could have been activated in the meantime)
  1829. #if GL
  1830. D .vf (VF); // set VF after VBO on OpenGL
  1831. #endif
  1832. }
  1833. #endif
  1834. }
  1835. void VtxIndBuf::clear()
  1836. {
  1837. VI._vtx_type =VI_NONE;
  1838. VI._vtx_queued=0; // clear can be called by engine method to stop VI in progress (like in light drawing when detected that the rectangle doesn't intersect with the viewport), so clear any current vertexes for drawing
  1839. VI._image =null;
  1840. VI._shader =null;
  1841. // we've changed textures so we need to clear material
  1842. MaterialLast =null;
  1843. MaterialLast4[0]=null;
  1844. if(VI._user_flag)
  1845. {
  1846. if(VI._user_flag&VI_CUSTOM_DEPTH_WRITE)D.depthWrite(VI._depth_write); // reset depth writing
  1847. if(VI._user_flag&VI_CUSTOM_TEX_WRAP ) // reset the sampler
  1848. {
  1849. #if DX11
  1850. if(D._sampler2D)SamplerLinearClamp.setPS(SSI_DEFAULT);
  1851. else SamplerAnisotropic.setPS(SSI_DEFAULT);
  1852. #else
  1853. Sh.h_ImageCol[0]->_sampler=null;
  1854. #endif
  1855. }
  1856. VI._user_flag=0; // clear the user flag
  1857. }
  1858. SetVtxNrmMulAdd(true);
  1859. }
  1860. void VtxIndBuf::setFirst(VI_TYPE vtx_type, UInt flag)
  1861. {
  1862. if(!VI._vtx_type)VI.setType(vtx_type, flag);
  1863. }
  1864. void VtxIndBuf::end()
  1865. {
  1866. flush();
  1867. clear();
  1868. }
  1869. /******************************************************************************/
  1870. void VtxIndBuf::shader(Shader *shader) {VI._shader=shader;}
  1871. void VtxIndBuf::image(C Image *image)
  1872. {
  1873. if(VI._image!=image)
  1874. {
  1875. flush(); // first flush what's already available, after that make the change
  1876. VI._image=image;
  1877. Sh.h_ImageCol[0]->set(image);
  1878. Sh.h_ImageColMS ->set(image);
  1879. }
  1880. }
  1881. void VtxIndBuf::color(C Color &color)
  1882. {
  1883. if(VI._color!=color)
  1884. {
  1885. flush(); // first flush what's already available, after that make the change
  1886. VI._color=color;
  1887. }
  1888. Sh.h_Color[0]->set(color);
  1889. }
  1890. void VtxIndBuf::color2(C Color &color)
  1891. {
  1892. Sh.h_Color[1]->set(color);
  1893. }
  1894. void VtxIndBuf::cull (Bool cull) {FlagSet(VI._user_flag, VI_CULL , cull);}
  1895. void VtxIndBuf::alphaTest (Bool on ) {FlagSet(VI._user_flag, VI_ALPHA_TEST, on );}
  1896. void VtxIndBuf::fog (Bool on ) {FlagSet(VI._user_flag, VI_FOG , on );}
  1897. void VtxIndBuf::depthWrite(Bool on ) {if(!(VI._user_flag&VI_CUSTOM_DEPTH_WRITE)){VI._depth_write=D._depth_write; VI._user_flag|=VI_CUSTOM_DEPTH_WRITE;} D.depthWrite(on);}
  1898. void VtxIndBuf::clamp()
  1899. {
  1900. FlagEnable(VI._user_flag, VI_CUSTOM_TEX_WRAP);
  1901. #if DX11
  1902. SamplerLinearClamp.setPS(SSI_DEFAULT);
  1903. #else
  1904. Sh.h_ImageCol[0]->_sampler=&SamplerLinearClamp;
  1905. #endif
  1906. }
  1907. void VtxIndBuf::wrap()
  1908. {
  1909. FlagEnable(VI._user_flag, VI_CUSTOM_TEX_WRAP);
  1910. #if DX11
  1911. SamplerLinearWrap.setPS(SSI_DEFAULT);
  1912. #else
  1913. Sh.h_ImageCol[0]->_sampler=&SamplerLinearWrap;
  1914. #endif
  1915. }
  1916. void VtxIndBuf::wrapX()
  1917. {
  1918. FlagEnable(VI._user_flag, VI_CUSTOM_TEX_WRAP);
  1919. #if DX11
  1920. SamplerLinearWCC.setPS(SSI_DEFAULT);
  1921. #else
  1922. Sh.h_ImageCol[0]->_sampler=&SamplerLinearWCC;
  1923. #endif
  1924. }
  1925. void VtxIndBuf::wrapY()
  1926. {
  1927. FlagEnable(VI._user_flag, VI_CUSTOM_TEX_WRAP);
  1928. #if DX11
  1929. SamplerLinearCWC.setPS(SSI_DEFAULT);
  1930. #else
  1931. Sh.h_ImageCol[0]->_sampler=&SamplerLinearCWC;
  1932. #endif
  1933. }
  1934. /******************************************************************************/
  1935. #if DX11
  1936. #if 0
  1937. extern void SetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY pt);
  1938. #else
  1939. INLINE void SetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY pt) {D3DC->IASetPrimitiveTopology(pt);}
  1940. #endif
  1941. #endif
  1942. void VtxIndBuf::flush()
  1943. {
  1944. if(VI._vtx_queued>0)
  1945. {
  1946. unlockVtx();
  1947. if(VI._shader)
  1948. {
  1949. VI._shader->begin();
  1950. if(VI._quad_ind) // this is always TRIANGLELIST
  1951. {
  1952. UInt quads=Unsigned(VI._vtx_queued)/4;
  1953. #if DX9
  1954. D3D->DrawIndexedPrimitive(D3DPT_TRIANGLELIST, VI._vtx_drawing, 0, VI._vtx_queued, 0, quads*2); VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;
  1955. #elif DX11
  1956. //if(VI._prim_type!=D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST)SetPrimitiveTopology(VI._prim_type); must be after 'shader->begin', not needed since 'quad_ind' always uses TRIANGLELIST mode
  1957. D3DC->DrawIndexed(quads*(2*3), 0, VI._vtx_drawing); VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;
  1958. #elif GL_ES
  1959. glDrawElements(GL_TRIANGLES, quads*(2*3), IndBuf16384Quads.bit16() ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, null);
  1960. #elif GL
  1961. glDrawElementsBaseVertex(GL_TRIANGLES, quads*(2*3), IndBuf16384Quads.bit16() ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, null, VI._vtx_drawing); if(GL_RING){VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;}
  1962. #endif
  1963. }else
  1964. {
  1965. #if DX9
  1966. D3D->DrawPrimitive(VI._prim_type, VI._vtx_drawing, Max(0, VI._vtx_queued/VI._ind_div-VI._ind_sub)); VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;
  1967. #elif DX11
  1968. if(VI._prim_type!=D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST)SetPrimitiveTopology(VI._prim_type); // must be after 'shader->begin'
  1969. D3DC->Draw(VI._vtx_queued, VI._vtx_drawing); VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;
  1970. #elif GL_ES
  1971. glDrawArrays(VI._prim_type, 0, VI._vtx_queued);
  1972. #elif GL
  1973. glDrawArrays(VI._prim_type, VI._vtx_drawing, VI._vtx_queued); if(GL_RING){VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;}
  1974. #endif
  1975. }
  1976. ShaderEnd();
  1977. }
  1978. VI._vtx_queued=0;
  1979. }
  1980. }
  1981. void VtxIndBuf::flushIndexed(IndBuf &ib, Int ind_num)
  1982. {
  1983. if(VI._vtx_queued>0)
  1984. {
  1985. unlockVtx();
  1986. if(UInt(ind_num)<=UInt(ib._ind_num) && VI._shader) // inclusive 'InRange'
  1987. {
  1988. ib.set(); VI._shader->begin();
  1989. #if DX9
  1990. D3D->DrawIndexedPrimitive(VI._prim_type, VI._vtx_drawing, 0, VI._vtx_queued, 0, ind_num/VI._ind_div); VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;
  1991. #elif DX11
  1992. if(VI._prim_type!=D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST)SetPrimitiveTopology(VI._prim_type); // must be after 'shader->begin'
  1993. D3DC->DrawIndexed(ind_num, 0, VI._vtx_drawing); VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;
  1994. #elif GL_ES
  1995. glDrawElements(VI._prim_type, ind_num, ib.bit16() ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, null);
  1996. #elif GL
  1997. glDrawElementsBaseVertex(VI._prim_type, ind_num, ib.bit16() ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, null, VI._vtx_drawing); if(GL_RING){VI._vtx_drawing+=VI._vtx_queued; VI._vtx_drawing_raw=VI._vtx_drawing*VI._vb._vtx_size;}
  1998. #endif
  1999. ShaderEnd();
  2000. }
  2001. VI._vtx_queued=0;
  2002. }
  2003. }
  2004. Ptr VtxIndBuf::addVtx(Int vtxs)
  2005. {
  2006. Int total_vtxs =vtxs+VI._vtx_drawing+VI._vtx_queued;
  2007. if( total_vtxs> VI._vb._vtx_num ){flush(); unlockVtx(); VI._vtx_drawing=VI._vtx_drawing_raw=0; total_vtxs=vtxs;} // if vertexes don't fit then flush all queued, it is important that 'unlockVtx' is called !! it is because in 'flush' it will be called only if there are vertexes queued, and in case when we've already locked buffer for purpose of adding new vertexes, however that was interrupted with 'clear', then the buffer remains locked, however it may be locked using LOCK_APPEND, but for this case we always need to rewrite it from start using LOCK_WRITE, to notify the driver that we're going to overwrite existing data, so call 'unlockVtx' to make sure that next lock is OK
  2008. if( total_vtxs<=VI._vb._vtx_num && lockVtx()){Ptr vtx=VI._vtx_buf+(VI._vtx_queued+VI._vtx_drawing)*VI._vb._vtx_size; VI._vtx_queued+=vtxs; return vtx;}
  2009. return null;
  2010. }
  2011. /*U16* VtxIndBuf::addInd(Int inds)
  2012. {
  2013. if(inds+VI._ind_queued<=VI._ib._ind_num && lockInd()){U16 *ind=VI._ind_buf+VI._ind_queued; VI._ind_queued+=inds; return ind;}
  2014. return null;
  2015. }
  2016. Int VtxIndBuf::add(Int vtxs, Ptr &vtx, Int inds, U16* &ind)
  2017. {
  2018. if(vtxs+VI._vtx_queued> VI._vb._vtx_num || inds+VI._ind_queued> VI._ib._ind_num)drawIndexed();
  2019. if(vtxs+VI._vtx_queued<=VI._vb._vtx_num && inds+VI._ind_queued<=VI._ib._ind_num && lockVtx() && lockInd())
  2020. {
  2021. Int ret=VI._vtx_queued;
  2022. vtx=VI._vtx_buf+VI._vtx_queued*VI._vb._vtx_size; VI._vtx_queued+=vtxs;
  2023. ind=VI._ind_buf+VI._ind_queued ; VI._ind_queued+=inds;
  2024. return ret;
  2025. }
  2026. return -1;
  2027. }
  2028. /******************************************************************************/
  2029. void VtxIndBuf::dot(C Vec2 &pos, Flt r)
  2030. {
  2031. setFirst(VI_2D_FLAT, VI_QUAD_IND);
  2032. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(4))
  2033. {
  2034. v[0].pos.set(pos.x-r, pos.y+r);
  2035. v[1].pos.set(pos.x+r, pos.y+r);
  2036. v[2].pos.set(pos.x+r, pos.y-r);
  2037. v[3].pos.set(pos.x-r, pos.y-r);
  2038. }
  2039. }
  2040. void VtxIndBuf::dot(C Color &color, C Vec2 &pos, Flt r)
  2041. {
  2042. setFirst(VI_2D_COL, VI_QUAD_IND);
  2043. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2044. {
  2045. v[0].color=v[1].color=v[2].color=v[3].color=color;
  2046. v[0].pos.set(pos.x-r, pos.y+r);
  2047. v[1].pos.set(pos.x+r, pos.y+r);
  2048. v[2].pos.set(pos.x+r, pos.y-r);
  2049. v[3].pos.set(pos.x-r, pos.y-r);
  2050. }
  2051. }
  2052. void VtxIndBuf::dot( C Vec &pos, Flt r) {Vec2 screen; if(PosToScreenM(pos, screen))dot( screen, r);}
  2053. void VtxIndBuf::dot(C Color &color, C Vec &pos, Flt r) {Vec2 screen; if(PosToScreenM(pos, screen))dot(color, screen, r);}
  2054. /******************************************************************************/
  2055. void VtxIndBuf::rect(C Rect &rect)
  2056. {
  2057. setFirst(VI_2D_FLAT, VI_QUAD_IND);
  2058. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(4))
  2059. {
  2060. v[0].pos.set(rect.min.x, rect.max.y);
  2061. v[1].pos.set(rect.max.x, rect.max.y);
  2062. v[2].pos.set(rect.max.x, rect.min.y);
  2063. v[3].pos.set(rect.min.x, rect.min.y);
  2064. }
  2065. }
  2066. void VtxIndBuf::rect(C Color &color, C Rect &rect)
  2067. {
  2068. setFirst(VI_2D_COL, VI_QUAD_IND);
  2069. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2070. {
  2071. v[0].color=v[1].color=v[2].color=v[3].color=color;
  2072. v[0].pos.set(rect.min.x, rect.max.y);
  2073. v[1].pos.set(rect.max.x, rect.max.y);
  2074. v[2].pos.set(rect.max.x, rect.min.y);
  2075. v[3].pos.set(rect.min.x, rect.min.y);
  2076. }
  2077. }
  2078. /******************************************************************************/
  2079. void VtxIndBuf::rectL(C Rect &rect)
  2080. {
  2081. setFirst(VI_2D_FLAT, VI_LINE);
  2082. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(8))
  2083. {
  2084. // drawing lines needs adjustments
  2085. Rect r(rect.min.x+D._pixel_size_2.x, rect.min.y+D._pixel_size_2.y,
  2086. rect.max.x-D._pixel_size_2.x, rect.max.y-D._pixel_size_2.y);
  2087. v[0].pos.set(r.min.x, r.max.y); v[1].pos.set(r.max.x, r.max.y);
  2088. v[2].pos.set(r.max.x, r.max.y); v[3].pos.set(r.max.x, r.min.y);
  2089. v[4].pos.set(r.max.x, r.min.y); v[5].pos.set(r.min.x, r.min.y);
  2090. v[6].pos.set(r.min.x, r.min.y); v[7].pos.set(r.min.x, r.max.y);
  2091. }
  2092. }
  2093. void VtxIndBuf::rectL(C Color &color, C Rect &rect)
  2094. {
  2095. setFirst(VI_2D_COL, VI_LINE);
  2096. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(8))
  2097. {
  2098. // drawing lines needs adjustments
  2099. Rect r(rect.min.x+D._pixel_size_2.x, rect.min.y+D._pixel_size_2.y,
  2100. rect.max.x-D._pixel_size_2.x, rect.max.y-D._pixel_size_2.y);
  2101. v[0].color=v[1].color=v[2].color=v[3].color=v[4].color=v[5].color=v[6].color=v[7].color=color;
  2102. v[0].pos.set(r.min.x, r.max.y); v[1].pos.set(r.max.x, r.max.y);
  2103. v[2].pos.set(r.max.x, r.max.y); v[3].pos.set(r.max.x, r.min.y);
  2104. v[4].pos.set(r.max.x, r.min.y); v[5].pos.set(r.min.x, r.min.y);
  2105. v[6].pos.set(r.min.x, r.min.y); v[7].pos.set(r.min.x, r.max.y);
  2106. }
  2107. }
  2108. /******************************************************************************/
  2109. void VtxIndBuf::rectShadedX(C Color &color0, C Color &color1, C Rect &rect)
  2110. {
  2111. setFirst(VI_2D_COL, VI_QUAD_IND);
  2112. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2113. {
  2114. v[0].color=v[3].color=color0;
  2115. v[1].color=v[2].color=color1;
  2116. v[0].pos.set(rect.min.x, rect.max.y);
  2117. v[1].pos.set(rect.max.x, rect.max.y);
  2118. v[2].pos.set(rect.max.x, rect.min.y);
  2119. v[3].pos.set(rect.min.x, rect.min.y);
  2120. }
  2121. }
  2122. void VtxIndBuf::rectShadedY(C Color &color0, C Color &color1, C Rect &rect)
  2123. {
  2124. setFirst(VI_2D_COL, VI_QUAD_IND);
  2125. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2126. {
  2127. v[0].color=v[1].color=color0;
  2128. v[2].color=v[3].color=color1;
  2129. v[0].pos.set(rect.min.x, rect.max.y);
  2130. v[1].pos.set(rect.max.x, rect.max.y);
  2131. v[2].pos.set(rect.max.x, rect.min.y);
  2132. v[3].pos.set(rect.min.x, rect.min.y);
  2133. }
  2134. }
  2135. /******************************************************************************/
  2136. void VtxIndBuf::line(C Vec2 &a, C Vec2 &b)
  2137. {
  2138. setFirst(VI_2D_FLAT, VI_LINE);
  2139. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(2))
  2140. {
  2141. v[0].pos=a;
  2142. v[1].pos=b;
  2143. }
  2144. }
  2145. void VtxIndBuf::line(C Vec2 &a, C Vec2 &b, Flt width)
  2146. {
  2147. Vec2 perp=Perp(b-a); perp.setLength(width);
  2148. setFirst(VI_2D_FLAT, VI_QUAD_IND);
  2149. if(Vtx2DFlat *v=(Vtx2DFlat*)VI.addVtx(4))
  2150. {
  2151. v[0].pos.set(a.x-perp.x, a.y-perp.y);
  2152. v[1].pos.set(b.x-perp.x, b.y-perp.y);
  2153. v[2].pos.set(b.x+perp.x, b.y+perp.y);
  2154. v[3].pos.set(a.x+perp.x, a.y+perp.y);
  2155. }
  2156. }
  2157. void VtxIndBuf::line(C Vec &a, C Vec &b)
  2158. {
  2159. setFirst(VI_3D_FLAT, VI_LINE);
  2160. if(Vtx3DFlat *v=(Vtx3DFlat*)addVtx(2))
  2161. {
  2162. v[0].pos=a;
  2163. v[1].pos=b;
  2164. }
  2165. }
  2166. void VtxIndBuf::line(C Color &color, C Vec2 &a, C Vec2 &b)
  2167. {
  2168. setFirst(VI_2D_COL, VI_LINE);
  2169. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(2))
  2170. {
  2171. v[0].color=v[1].color=color;
  2172. v[0].pos=a;
  2173. v[1].pos=b;
  2174. }
  2175. }
  2176. void VtxIndBuf::line(C Color &color, C Vec &a, C Vec &b)
  2177. {
  2178. setFirst(VI_3D_COL, VI_LINE);
  2179. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(2))
  2180. {
  2181. v[0].color=v[1].color=color;
  2182. v[0].pos=a;
  2183. v[1].pos=b;
  2184. }
  2185. }
  2186. void VtxIndBuf::line(C Color &col_a, C Color &col_b, C Vec2 &a, C Vec2 &b)
  2187. {
  2188. setFirst(VI_2D_COL, VI_LINE);
  2189. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(2))
  2190. {
  2191. v[0].pos=a; v[0].color=col_a;
  2192. v[1].pos=b; v[1].color=col_b;
  2193. }
  2194. }
  2195. void VtxIndBuf::line(C Color &col_a, C Color &col_b, C Vec &a, C Vec &b)
  2196. {
  2197. setFirst(VI_3D_COL, VI_LINE);
  2198. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(2))
  2199. {
  2200. v[0].pos=a; v[0].color=col_a;
  2201. v[1].pos=b; v[1].color=col_b;
  2202. }
  2203. }
  2204. /******************************************************************************/
  2205. void VtxIndBuf::tri(C Tri2 &tri)
  2206. {
  2207. setFirst(VI_2D_FLAT);
  2208. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(3))
  2209. {
  2210. v[0].pos=tri.p[0];
  2211. v[1].pos=tri.p[1];
  2212. v[2].pos=tri.p[2];
  2213. }
  2214. }
  2215. void VtxIndBuf::tri(C Tri &tri)
  2216. {
  2217. setFirst(VI_3D_FLAT);
  2218. if(Vtx3DFlat *v=(Vtx3DFlat*)addVtx(3))
  2219. {
  2220. v[0].pos=tri.p[0];
  2221. v[1].pos=tri.p[1];
  2222. v[2].pos=tri.p[2];
  2223. }
  2224. }
  2225. void VtxIndBuf::tri(C Vec2 &a, C Vec2 &b, C Vec2 &c)
  2226. {
  2227. setFirst(VI_2D_FLAT);
  2228. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(3))
  2229. {
  2230. v[0].pos=a;
  2231. v[1].pos=b;
  2232. v[2].pos=c;
  2233. }
  2234. }
  2235. void VtxIndBuf::tri(C Vec &a, C Vec &b, C Vec &c)
  2236. {
  2237. setFirst(VI_3D_FLAT);
  2238. if(Vtx3DFlat *v=(Vtx3DFlat*)addVtx(3))
  2239. {
  2240. v[0].pos=a;
  2241. v[1].pos=b;
  2242. v[2].pos=c;
  2243. }
  2244. }
  2245. void VtxIndBuf::tri(C Color &color, C Vec2 &a, C Vec2 &b, C Vec2 &c)
  2246. {
  2247. setFirst(VI_2D_COL);
  2248. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(3))
  2249. {
  2250. v[0].color=v[1].color=v[2].color=color;
  2251. v[0].pos=a;
  2252. v[1].pos=b;
  2253. v[2].pos=c;
  2254. }
  2255. }
  2256. void VtxIndBuf::tri(C Color &color, C Vec &a, C Vec &b, C Vec &c)
  2257. {
  2258. setFirst(VI_3D_COL);
  2259. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(3))
  2260. {
  2261. v[0].color=v[1].color=v[2].color=color;
  2262. v[0].pos=a;
  2263. v[1].pos=b;
  2264. v[2].pos=c;
  2265. }
  2266. }
  2267. void VtxIndBuf::tri(C Color &col_a, C Color &col_b, C Color &col_c, C Vec2 &a, C Vec2 &b, C Vec2 &c)
  2268. {
  2269. setFirst(VI_2D_COL);
  2270. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(3))
  2271. {
  2272. v[0].pos=a; v[0].color=col_a;
  2273. v[1].pos=b; v[1].color=col_b;
  2274. v[2].pos=c; v[2].color=col_c;
  2275. }
  2276. }
  2277. void VtxIndBuf::tri(C Color &col_a, C Color &col_b, C Color &col_c, C Vec &a, C Vec &b, C Vec &c)
  2278. {
  2279. setFirst(VI_3D_COL);
  2280. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(3))
  2281. {
  2282. v[0].pos=a; v[0].color=col_a;
  2283. v[1].pos=b; v[1].color=col_b;
  2284. v[2].pos=c; v[2].color=col_c;
  2285. }
  2286. }
  2287. /******************************************************************************/
  2288. void VtxIndBuf::quad(C Quad2 &quad)
  2289. {
  2290. setFirst(VI_2D_FLAT, VI_QUAD_IND);
  2291. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(4))
  2292. {
  2293. v[0].pos=quad.p[0];
  2294. v[1].pos=quad.p[1];
  2295. v[2].pos=quad.p[2];
  2296. v[3].pos=quad.p[3];
  2297. }
  2298. }
  2299. void VtxIndBuf::quad(C Quad &quad)
  2300. {
  2301. setFirst(VI_3D_FLAT, VI_QUAD_IND);
  2302. if(Vtx3DFlat *v=(Vtx3DFlat*)addVtx(4))
  2303. {
  2304. v[0].pos=quad.p[0];
  2305. v[1].pos=quad.p[1];
  2306. v[2].pos=quad.p[2];
  2307. v[3].pos=quad.p[3];
  2308. }
  2309. }
  2310. void VtxIndBuf::quad(C Vec2 &a, C Vec2 &b, C Vec2 &c, C Vec2 &d)
  2311. {
  2312. setFirst(VI_2D_FLAT, VI_QUAD_IND);
  2313. if(Vtx2DFlat *v=(Vtx2DFlat*)addVtx(4))
  2314. {
  2315. v[0].pos=a;
  2316. v[1].pos=b;
  2317. v[2].pos=c;
  2318. v[3].pos=d;
  2319. }
  2320. }
  2321. void VtxIndBuf::quad(C Vec &a, C Vec &b, C Vec &c, C Vec &d)
  2322. {
  2323. setFirst(VI_3D_FLAT, VI_QUAD_IND);
  2324. if(Vtx3DFlat *v=(Vtx3DFlat*)addVtx(4))
  2325. {
  2326. v[0].pos=a;
  2327. v[1].pos=b;
  2328. v[2].pos=c;
  2329. v[3].pos=d;
  2330. }
  2331. }
  2332. void VtxIndBuf::quad(C Color &color, C Quad2 &quad)
  2333. {
  2334. setFirst(VI_2D_COL, VI_QUAD_IND);
  2335. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2336. {
  2337. v[0].color=v[1].color=v[2].color=v[3].color=color;
  2338. v[0].pos=quad.p[0];
  2339. v[1].pos=quad.p[1];
  2340. v[2].pos=quad.p[2];
  2341. v[3].pos=quad.p[3];
  2342. }
  2343. }
  2344. void VtxIndBuf::quad(C Color &color, C Quad &quad)
  2345. {
  2346. setFirst(VI_3D_COL, VI_QUAD_IND);
  2347. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(4))
  2348. {
  2349. v[0].color=v[1].color=v[2].color=v[3].color=color;
  2350. v[0].pos=quad.p[0];
  2351. v[1].pos=quad.p[1];
  2352. v[2].pos=quad.p[2];
  2353. v[3].pos=quad.p[3];
  2354. }
  2355. }
  2356. void VtxIndBuf::quad(C Color &color, C Vec2 &a, C Vec2 &b, C Vec2 &c, C Vec2 &d)
  2357. {
  2358. setFirst(VI_2D_COL, VI_QUAD_IND);
  2359. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2360. {
  2361. v[0].color=v[1].color=v[2].color=v[3].color=color;
  2362. v[0].pos=a;
  2363. v[1].pos=b;
  2364. v[2].pos=c;
  2365. v[3].pos=d;
  2366. }
  2367. }
  2368. void VtxIndBuf::quad(C Color &color, C Vec &a, C Vec &b, C Vec &c, C Vec &d)
  2369. {
  2370. setFirst(VI_3D_COL, VI_QUAD_IND);
  2371. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(4))
  2372. {
  2373. v[0].color=v[1].color=v[2].color=v[3].color=color;
  2374. v[0].pos=a;
  2375. v[1].pos=b;
  2376. v[2].pos=c;
  2377. v[3].pos=d;
  2378. }
  2379. }
  2380. void VtxIndBuf::quad(C Color &c0, C Color &c1, C Vec2 &a, C Vec2 &b, C Vec2 &c, C Vec2 &d)
  2381. {
  2382. setFirst(VI_2D_COL, VI_QUAD_IND);
  2383. if(Vtx2DCol *v=(Vtx2DCol*)addVtx(4))
  2384. {
  2385. v[0].color=v[3].color=c0;
  2386. v[1].color=v[2].color=c1;
  2387. v[0].pos=a;
  2388. v[1].pos=b;
  2389. v[2].pos=c;
  2390. v[3].pos=d;
  2391. }
  2392. }
  2393. void VtxIndBuf::quad(C Color &c0, C Color &c1, C Vec &a, C Vec &b, C Vec &c, C Vec &d)
  2394. {
  2395. setFirst(VI_3D_COL, VI_QUAD_IND);
  2396. if(Vtx3DCol *v=(Vtx3DCol*)addVtx(4))
  2397. {
  2398. v[0].color=v[3].color=c0;
  2399. v[1].color=v[2].color=c1;
  2400. v[0].pos=a;
  2401. v[1].pos=b;
  2402. v[2].pos=c;
  2403. v[3].pos=d;
  2404. }
  2405. }
  2406. /******************************************************************************/
  2407. void VtxIndBuf::image(C Rect &screen_rect)
  2408. {
  2409. setFirst(VI_2D_TEX, VI_QUAD_IND|VI_SP_COL);
  2410. if(Vtx2DTex *v=(Vtx2DTex*)addVtx(4))
  2411. {
  2412. v[0].pos.set(screen_rect.min.x, screen_rect.max.y);
  2413. v[1].pos.set(screen_rect.max.x, screen_rect.max.y);
  2414. v[2].pos.set(screen_rect.max.x, screen_rect.min.y);
  2415. v[3].pos.set(screen_rect.min.x, screen_rect.min.y);
  2416. if(VI._image && VI._image->partial())
  2417. {
  2418. v[0].tex.x=v[3].tex.x=0;
  2419. v[1].tex.x=v[2].tex.x=VI._image->_part.x;
  2420. v[0].tex.y=v[1].tex.y=0;
  2421. v[2].tex.y=v[3].tex.y=VI._image->_part.y;
  2422. }else
  2423. {
  2424. v[0].tex.set(0, 0);
  2425. v[1].tex.set(1, 0);
  2426. v[2].tex.set(1, 1);
  2427. v[3].tex.set(0, 1);
  2428. }
  2429. }
  2430. }
  2431. void VtxIndBuf::imagePart(C Rect &screen_rect, C Rect &tex_rect)
  2432. {
  2433. setFirst(VI_2D_TEX, VI_QUAD_IND|VI_SP_COL);
  2434. if(Vtx2DTex *v=(Vtx2DTex*)addVtx(4))
  2435. {
  2436. v[0].pos.set(screen_rect.min.x, screen_rect.max.y);
  2437. v[1].pos.set(screen_rect.max.x, screen_rect.max.y);
  2438. v[2].pos.set(screen_rect.max.x, screen_rect.min.y);
  2439. v[3].pos.set(screen_rect.min.x, screen_rect.min.y);
  2440. if(VI._image && VI._image->partial())
  2441. {
  2442. v[0].tex.x=v[3].tex.x=tex_rect.min.x*VI._image->_part.x;
  2443. v[1].tex.x=v[2].tex.x=tex_rect.max.x*VI._image->_part.x;
  2444. v[0].tex.y=v[1].tex.y=tex_rect.min.y*VI._image->_part.y;
  2445. v[2].tex.y=v[3].tex.y=tex_rect.max.y*VI._image->_part.y;
  2446. }else
  2447. {
  2448. v[0].tex.set(tex_rect.min.x, tex_rect.min.y);
  2449. v[1].tex.set(tex_rect.max.x, tex_rect.min.y);
  2450. v[2].tex.set(tex_rect.max.x, tex_rect.max.y);
  2451. v[3].tex.set(tex_rect.min.x, tex_rect.max.y);
  2452. }
  2453. }
  2454. }
  2455. void VtxIndBuf::font(C Rect &screen_rect, C Rect &tex_rect)
  2456. {
  2457. setFirst(VI_2D_FONT, VI_QUAD_IND);
  2458. if(Vtx2DFont *v=(Vtx2DFont*)addVtx(4))
  2459. {
  2460. v[0].pos.set(screen_rect.min.x, screen_rect.max.y); v[0].shade=( 1+0.2f)*2.5f+0.5f;
  2461. v[1].pos.set(screen_rect.max.x, screen_rect.max.y); v[1].shade=( 1+0.2f)*2.5f+0.5f;
  2462. v[2].pos.set(screen_rect.max.x, screen_rect.min.y); v[2].shade=(-1+0.2f)*2.5f+0.5f;
  2463. v[3].pos.set(screen_rect.min.x, screen_rect.min.y); v[3].shade=(-1+0.2f)*2.5f+0.5f;
  2464. if(VI._image && VI._image->partial())
  2465. {
  2466. v[0].tex.x=v[3].tex.x=tex_rect.min.x*VI._image->_part.x;
  2467. v[1].tex.x=v[2].tex.x=tex_rect.max.x*VI._image->_part.x;
  2468. v[0].tex.y=v[1].tex.y=tex_rect.min.y*VI._image->_part.y;
  2469. v[2].tex.y=v[3].tex.y=tex_rect.max.y*VI._image->_part.y;
  2470. }else
  2471. {
  2472. v[0].tex.set(tex_rect.min.x, tex_rect.min.y);
  2473. v[1].tex.set(tex_rect.max.x, tex_rect.min.y);
  2474. v[2].tex.set(tex_rect.max.x, tex_rect.max.y);
  2475. v[3].tex.set(tex_rect.min.x, tex_rect.max.y);
  2476. }
  2477. }
  2478. }
  2479. /******************************************************************************/
  2480. void VtxIndBuf::face(C Vtx2DTex &a, C Vtx2DTex &b, C Vtx2DTex &c)
  2481. {
  2482. setFirst(VI_2D_TEX);
  2483. if(Vtx2DTex *v=(Vtx2DTex*)addVtx(3))
  2484. {
  2485. v[0]=a;
  2486. v[1]=b;
  2487. v[2]=c;
  2488. if(VI._image && VI._image->partial())REP(3)v[i].tex*=VI._image->_part.xy;
  2489. }
  2490. }
  2491. void VtxIndBuf::face(C Vtx2DTex &a, C Vtx2DTex &b, C Vtx2DTex &c, C Vtx2DTex &d)
  2492. {
  2493. setFirst(VI_2D_TEX, VI_QUAD_IND);
  2494. if(Vtx2DTex *v=(Vtx2DTex*)addVtx(4))
  2495. {
  2496. v[0]=a;
  2497. v[1]=b;
  2498. v[2]=c;
  2499. v[3]=d;
  2500. if(VI._image && VI._image->partial())REP(4)v[i].tex*=VI._image->_part.xy;
  2501. }
  2502. }
  2503. /******************************************************************************/
  2504. void VtxIndBuf::face(C Vtx2DTexCol &a, C Vtx2DTexCol &b, C Vtx2DTexCol &c)
  2505. {
  2506. setFirst(VI_2D_TEX_COL);
  2507. if(Vtx2DTexCol *v=(Vtx2DTexCol*)addVtx(3))
  2508. {
  2509. v[0]=a;
  2510. v[1]=b;
  2511. v[2]=c;
  2512. if(VI._image && VI._image->partial())REP(3)v[i].tex*=VI._image->_part.xy;
  2513. }
  2514. }
  2515. void VtxIndBuf::face(C Vtx2DTexCol &a, C Vtx2DTexCol &b, C Vtx2DTexCol &c, C Vtx2DTexCol &d)
  2516. {
  2517. setFirst(VI_2D_TEX_COL, VI_QUAD_IND);
  2518. if(Vtx2DTexCol *v=(Vtx2DTexCol*)addVtx(4))
  2519. {
  2520. v[0]=a;
  2521. v[1]=b;
  2522. v[2]=c;
  2523. v[3]=d;
  2524. if(VI._image && VI._image->partial())REP(4)v[i].tex*=VI._image->_part.xy;
  2525. }
  2526. }
  2527. /******************************************************************************/
  2528. void VtxIndBuf::face(C Vtx3DTex &a, C Vtx3DTex &b, C Vtx3DTex &c)
  2529. {
  2530. setFirst(VI_3D_TEX);
  2531. if(Vtx3DTex *v=(Vtx3DTex*)addVtx(3))
  2532. {
  2533. v[0]=a;
  2534. v[1]=b;
  2535. v[2]=c;
  2536. if(VI._image && VI._image->partial())REP(3)v[i].tex*=VI._image->_part.xy;
  2537. }
  2538. }
  2539. void VtxIndBuf::face(C Vtx3DTex &a, C Vtx3DTex &b, C Vtx3DTex &c, C Vtx3DTex &d)
  2540. {
  2541. setFirst(VI_3D_TEX, VI_QUAD_IND);
  2542. if(Vtx3DTex *v=(Vtx3DTex*)addVtx(4))
  2543. {
  2544. v[0]=a;
  2545. v[1]=b;
  2546. v[2]=c;
  2547. v[3]=d;
  2548. if(VI._image && VI._image->partial())REP(4)v[i].tex*=VI._image->_part.xy;
  2549. }
  2550. }
  2551. /******************************************************************************/
  2552. void VtxIndBuf::face(C Vtx3DTexCol &a, C Vtx3DTexCol &b, C Vtx3DTexCol &c)
  2553. {
  2554. setFirst(VI_3D_TEX_COL);
  2555. if(Vtx3DTexCol *v=(Vtx3DTexCol*)addVtx(3))
  2556. {
  2557. v[0]=a;
  2558. v[1]=b;
  2559. v[2]=c;
  2560. if(VI._image && VI._image->partial())REP(3)v[i].tex*=VI._image->_part.xy;
  2561. }
  2562. }
  2563. void VtxIndBuf::face(C Vtx3DTexCol &a, C Vtx3DTexCol &b, C Vtx3DTexCol &c, C Vtx3DTexCol &d)
  2564. {
  2565. setFirst(VI_3D_TEX_COL, VI_QUAD_IND);
  2566. if(Vtx3DTexCol *v=(Vtx3DTexCol*)addVtx(4))
  2567. {
  2568. v[0]=a;
  2569. v[1]=b;
  2570. v[2]=c;
  2571. v[3]=d;
  2572. if(VI._image && VI._image->partial())REP(4)v[i].tex*=VI._image->_part.xy;
  2573. }
  2574. }
  2575. /******************************************************************************/
  2576. void VtxIndBuf::face(C Vtx3DSimple &a, C Vtx3DSimple &b, C Vtx3DSimple &c)
  2577. {
  2578. setFirst(VI_3D_SIMPLE);
  2579. if(Vtx3DSimple *v=(Vtx3DSimple*)addVtx(3))
  2580. {
  2581. v[0]=a;
  2582. v[1]=b;
  2583. v[2]=c;
  2584. if(VI._image && VI._image->partial())REP(3)v[i].tex*=VI._image->_part.xy;
  2585. }
  2586. }
  2587. void VtxIndBuf::face(C Vtx3DSimple &a, C Vtx3DSimple &b, C Vtx3DSimple &c, C Vtx3DSimple &d)
  2588. {
  2589. setFirst(VI_3D_SIMPLE, VI_QUAD_IND);
  2590. if(Vtx3DSimple *v=(Vtx3DSimple*)addVtx(4))
  2591. {
  2592. v[0]=a;
  2593. v[1]=b;
  2594. v[2]=c;
  2595. v[3]=d;
  2596. if(VI._image && VI._image->partial())REP(4)v[i].tex*=VI._image->_part.xy;
  2597. }
  2598. }
  2599. /******************************************************************************/
  2600. void VtxIndBuf::face(C Vtx3DStandard &a, C Vtx3DStandard &b, C Vtx3DStandard &c)
  2601. {
  2602. setFirst(VI_3D_STANDARD);
  2603. if(Vtx3DStandard *v=(Vtx3DStandard*)addVtx(3))
  2604. {
  2605. v[0]=a;
  2606. v[1]=b;
  2607. v[2]=c;
  2608. if(VI._image && VI._image->partial())REP(3)v[i].tex*=VI._image->_part.xy;
  2609. }
  2610. }
  2611. void VtxIndBuf::face(C Vtx3DStandard &a, C Vtx3DStandard &b, C Vtx3DStandard &c, C Vtx3DStandard &d)
  2612. {
  2613. setFirst(VI_3D_STANDARD, VI_QUAD_IND);
  2614. if(Vtx3DStandard *v=(Vtx3DStandard*)addVtx(4))
  2615. {
  2616. v[0]=a;
  2617. v[1]=b;
  2618. v[2]=c;
  2619. v[3]=d;
  2620. if(VI._image && VI._image->partial())REP(4)v[i].tex*=VI._image->_part.xy;
  2621. }
  2622. }
  2623. /******************************************************************************/
  2624. void VtxIndBuf::face(C Vtx3DFull &a, C Vtx3DFull &b, C Vtx3DFull &c)
  2625. {
  2626. setFirst(VI_3D_FULL);
  2627. if(Vtx3DFull *v=(Vtx3DFull*)addVtx(3))
  2628. {
  2629. v[0]=a;
  2630. v[1]=b;
  2631. v[2]=c;
  2632. }
  2633. }
  2634. void VtxIndBuf::face(C Vtx3DFull &a, C Vtx3DFull &b, C Vtx3DFull &c, C Vtx3DFull &d)
  2635. {
  2636. setFirst(VI_3D_FULL, VI_QUAD_IND);
  2637. if(Vtx3DFull *v=(Vtx3DFull*)addVtx(4))
  2638. {
  2639. v[0]=a;
  2640. v[1]=b;
  2641. v[2]=c;
  2642. v[3]=d;
  2643. }
  2644. }
  2645. /******************************************************************************/
  2646. void InitVtxInd()
  2647. {
  2648. if(LogInit)LogN("InitVtxInd");
  2649. if(!D._can_draw)return;
  2650. VI.create();
  2651. Int quads=16384; // 16384 is the maximum number of quads that still use 16-bit indexes (16384*4 == 65536)
  2652. IndBuf16384Quads.create(quads*6, true, false);
  2653. if(U16 *ind=(U16*)IndBuf16384Quads.lock(LOCK_WRITE))
  2654. {
  2655. Int p=0; REP(quads){ind[0]=p; ind[1]=p+1; ind[2]=p+3; ind[3]=p+3; ind[4]=p+1; ind[5]=p+2; p+=4; ind+=6;}
  2656. IndBuf16384Quads.unlock();
  2657. }else Exit("Can't create Index Buffer");
  2658. IndBufBorder.create(4*2*3, true, false);
  2659. if(IndBufBorder.lock(LOCK_WRITE))
  2660. {
  2661. IndBufBorder.setTri(0, 0,1,4);
  2662. IndBufBorder.setTri(1, 1,5,4);
  2663. IndBufBorder.setTri(2, 1,2,5);
  2664. IndBufBorder.setTri(3, 2,6,5);
  2665. IndBufBorder.setTri(4, 3,0,7);
  2666. IndBufBorder.setTri(5, 0,4,7);
  2667. IndBufBorder.setTri(6, 8,3,9);
  2668. IndBufBorder.setTri(7, 3,7,9);
  2669. IndBufBorder.unlock();
  2670. }else Exit("Can't create Index Buffer");
  2671. IndBufPanel.create(3*3*2*3, true, false);
  2672. if(IndBufPanel.lock(LOCK_WRITE))
  2673. {
  2674. IndBufPanel.setTri( 0, 0, 1, 4); // top
  2675. IndBufPanel.setTri( 1, 1, 5, 4);
  2676. IndBufPanel.setTri( 2, 1, 2, 5);
  2677. IndBufPanel.setTri( 3, 2, 6, 5);
  2678. IndBufPanel.setTri( 4, 2, 3, 6);
  2679. IndBufPanel.setTri( 5, 3, 7, 6);
  2680. IndBufPanel.setTri( 6, 8, 9,12); // bottom
  2681. IndBufPanel.setTri( 7, 9,13,12);
  2682. IndBufPanel.setTri( 8, 9,10,13);
  2683. IndBufPanel.setTri( 9, 10,14,13);
  2684. IndBufPanel.setTri(10, 10,11,14);
  2685. IndBufPanel.setTri(11, 11,15,14);
  2686. IndBufPanel.setTri(12, 4, 5, 8); // mid-left
  2687. IndBufPanel.setTri(13, 5, 9, 8); // mid-left
  2688. IndBufPanel.setTri(14, 6, 7,10); // mid-right
  2689. IndBufPanel.setTri(15, 7,11,10); // mid-right
  2690. IndBufPanel.setTri(16, 5, 6, 9); // mid-center (this must be last so we can draw just borders)
  2691. IndBufPanel.setTri(17, 6,10, 9); // mid-center (this must be last so we can draw just borders)
  2692. IndBufPanel.unlock();
  2693. }else Exit("Can't create Index Buffer");
  2694. IndBufPanelEx.create(3*3*2*3, true, false);
  2695. if(IndBufPanelEx.lock(LOCK_WRITE))
  2696. {
  2697. IndBufPanelEx.setTri( 0, 0, 1, 4); // top
  2698. IndBufPanelEx.setTri( 1, 1, 5, 4);
  2699. IndBufPanelEx.setTri( 2, 1, 2, 5);
  2700. IndBufPanelEx.setTri( 3, 2, 6, 5);
  2701. IndBufPanelEx.setTri( 4, 2, 3, 6);
  2702. IndBufPanelEx.setTri( 5, 3, 7, 6);
  2703. IndBufPanelEx.setTri( 6, 10,14,16); // bottom
  2704. IndBufPanelEx.setTri( 7, 14,17,16);
  2705. IndBufPanelEx.setTri( 8, 14,15,17);
  2706. IndBufPanelEx.setTri( 9, 15,18,17);
  2707. IndBufPanelEx.setTri(10, 15,13,18);
  2708. IndBufPanelEx.setTri(11, 13,19,18);
  2709. IndBufPanelEx.setTri(12, 4, 8,10); // mid-left
  2710. IndBufPanelEx.setTri(13, 8,11,10); // mid-left
  2711. IndBufPanelEx.setTri(14, 9, 7,12); // mid-right
  2712. IndBufPanelEx.setTri(15, 7,13,12); // mid-right
  2713. IndBufPanelEx.setTri(16, 8, 9,11); // mid-center (this must be last so we can draw just borders)
  2714. IndBufPanelEx.setTri(17, 9,12,11); // mid-center (this must be last so we can draw just borders)
  2715. IndBufPanelEx.unlock();
  2716. }else Exit("Can't create Index Buffer");
  2717. IndBufRectBorder.create(4*2*3, true, false);
  2718. if(IndBufRectBorder.lock(LOCK_WRITE))
  2719. {
  2720. IndBufRectBorder.setTri(0, 0,1,4);
  2721. IndBufRectBorder.setTri(1, 1,5,4);
  2722. IndBufRectBorder.setTri(2, 1,2,5);
  2723. IndBufRectBorder.setTri(3, 2,6,5);
  2724. IndBufRectBorder.setTri(4, 2,3,6);
  2725. IndBufRectBorder.setTri(5, 3,7,6);
  2726. IndBufRectBorder.setTri(6, 3,0,7);
  2727. IndBufRectBorder.setTri(7, 0,4,7);
  2728. IndBufRectBorder.unlock();
  2729. }else Exit("Can't create Index Buffer");
  2730. IndBufRectShaded.create(5*2*3, true, false);
  2731. if(IndBufRectShaded.lock(LOCK_WRITE))
  2732. {
  2733. IndBufRectShaded.setTri(0, 0,1,4);
  2734. IndBufRectShaded.setTri(1, 1,5,4);
  2735. IndBufRectShaded.setTri(2, 1,2,5);
  2736. IndBufRectShaded.setTri(3, 2,6,5);
  2737. IndBufRectShaded.setTri(4, 2,3,6);
  2738. IndBufRectShaded.setTri(5, 3,7,6);
  2739. IndBufRectShaded.setTri(6, 3,0,7);
  2740. IndBufRectShaded.setTri(7, 0,4,7);
  2741. IndBufRectShaded.setTri(8, 4,5,6); // middle
  2742. IndBufRectShaded.setTri(9, 6,7,4); // middle
  2743. IndBufRectShaded.unlock();
  2744. }else Exit("Can't create Index Buffer");
  2745. }
  2746. void ShutVtxInd()
  2747. {
  2748. IndBufRectShaded.del();
  2749. IndBufRectBorder.del();
  2750. IndBufPanel .del();
  2751. IndBufPanelEx .del();
  2752. IndBufBorder .del();
  2753. IndBuf16384Quads.del();
  2754. VI .del();
  2755. VtxFormats .del();
  2756. }
  2757. /******************************************************************************/
  2758. }
  2759. /******************************************************************************/