p_32.inc 23 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943
  1. {
  2. Free Pascal port of the Hermes C library.
  3. Copyright (C) 2001-2003 Nikolay Nikolov ([email protected])
  4. Original C version by Christian Nentwich ([email protected])
  5. This library is free software; you can redistribute it and/or
  6. modify it under the terms of the GNU Lesser General Public
  7. License as published by the Free Software Foundation; either
  8. version 2.1 of the License, or (at your option) any later version.
  9. This library is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  12. Lesser General Public License for more details.
  13. You should have received a copy of the GNU Lesser General Public
  14. License along with this library; if not, write to the Free Software
  15. Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  16. }
  17. {
  18. 32 bit to * converters for the HERMES library
  19. Copyright (c) 1998 Christian Nentwich ([email protected])
  20. This source code is licensed under the GNU LGPL
  21. Please refer to the file COPYING.LIB contained in the distribution for
  22. licensing conditions
  23. }
  24. { -------------------------------------------------------------------------
  25. NORMAL CONVERTERS
  26. ------------------------------------------------------------------------- }
  27. { TO 32 BGR }
  28. Procedure ConvertP_32rgb888_32bgr888(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  29. Var
  30. s_pixel : int32;
  31. s_ptr : Pchar8;
  32. tmp : char8;
  33. Begin
  34. s_ptr := @s_pixel;
  35. Repeat
  36. s_pixel := Pint32(source)^;
  37. tmp := (s_ptr + R_32)^;
  38. (s_ptr + R_32)^ := (s_ptr + B_32)^;
  39. (s_ptr + B_32)^ := tmp;
  40. Pint32(dest)^ := s_pixel;
  41. Inc(dest, 4);
  42. Inc(source, 4);
  43. Dec(count);
  44. Until count = 0;
  45. End;
  46. { 32 RGBA }
  47. Procedure ConvertP_32rgb888_32rgba888(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  48. Begin
  49. Repeat
  50. Pint32(dest)^ := (Pint32(source)^ Shl 8) Or $ff;
  51. Inc(dest, 4);
  52. Inc(source, 4);
  53. Dec(count);
  54. Until count = 0;
  55. End;
  56. { 32 BGRA }
  57. Procedure ConvertP_32rgb888_32bgra888(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  58. Var
  59. s_pixel : int32;
  60. s_ptr : Pchar8;
  61. tmp : char8;
  62. Begin
  63. s_ptr := @s_pixel;
  64. Repeat
  65. s_pixel := Pint32(source)^;
  66. tmp := (s_ptr + R_32)^;
  67. (s_ptr + R_32)^ := (s_ptr + B_32)^;
  68. (s_ptr + B_32)^ := tmp;
  69. Pint32(dest)^ := (s_pixel Shl 8) Or $ff;
  70. Inc(dest, 4);
  71. Inc(source, 4);
  72. Dec(count);
  73. Until count = 0;
  74. End;
  75. { TO 24 RGB }
  76. Procedure ConvertP_32rgb888_24rgb888(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  77. Var
  78. s_pixel, s_pixel2 : int32;
  79. s_point : Pchar8;
  80. c : DWord;
  81. Begin
  82. s_point := @s_pixel;
  83. { Align mod 4 (quite important in this case.. ) }
  84. While (PtrUInt(dest) And $3) <> 0 Do
  85. Begin
  86. s_pixel := Pint32(source)^;
  87. (dest + R_24)^ := (s_point + R_32)^;
  88. (dest + G_24)^ := (s_point + G_32)^;
  89. (dest + B_24)^ := (s_point + B_32)^;
  90. Inc(source, 4);
  91. Inc(dest, 3);
  92. Dec(count);
  93. If count = 0 Then
  94. Exit;
  95. End;
  96. { Main loop. TODO: Big endian check! }
  97. c := count Shr 2;
  98. While c <> 0 Do
  99. Begin
  100. Dec(c);
  101. s_pixel := Pint32(source)^;
  102. s_pixel2 := (Pint32(source) + 1)^;
  103. s_pixel := (s_pixel And $ffffff) Or (s_pixel2 Shl 24);
  104. Pint32(dest)^ := s_pixel;
  105. s_pixel := (Pint32(source) + 2)^;
  106. s_pixel2 := ((s_pixel2 Shr 8) And $ffff) Or (s_pixel Shl 16);
  107. (Pint32(dest) + 1)^ := s_pixel2;
  108. s_pixel2 := (Pint32(source) + 3)^;
  109. s_pixel := ((s_pixel Shr 16) And $ff) Or (s_pixel2 Shl 8);
  110. (Pint32(dest) + 2)^ := s_pixel;
  111. Inc(source, 16);
  112. Inc(dest, 12);
  113. End;
  114. { Convert trailing pixels }
  115. count := count And $3;
  116. While count <> 0 Do
  117. Begin
  118. Dec(count);
  119. s_pixel := Pint32(source)^;
  120. (dest + R_24)^ := (s_point + R_32)^;
  121. (dest + G_24)^ := (s_point + G_32)^;
  122. (dest + B_24)^ := (s_point + B_32)^;
  123. Inc(source, 4);
  124. Inc(dest, 3);
  125. End;
  126. End;
  127. { TO 24 BGR }
  128. Procedure ConvertP_32rgb888_24bgr888(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  129. Var
  130. s_pixel : int32;
  131. s_point : Pchar8;
  132. Begin
  133. s_point := @s_pixel;
  134. Repeat
  135. s_pixel := Pint32(source)^;
  136. { Note that R and B are swapped }
  137. (dest + B_24)^ := (s_point + R_32)^;
  138. (dest + G_24)^ := (s_point + G_32)^;
  139. (dest + R_24)^ := (s_point + B_32)^;
  140. Inc(source, 4);
  141. Inc(dest, 3);
  142. Dec(count);
  143. Until count = 0;
  144. End;
  145. { TO 16 RGB 565 }
  146. Procedure ConvertP_32rgb888_16rgb565(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  147. Var
  148. i : DWord;
  149. s_pixel : int32;
  150. source_32, dest_32 : Pint32;
  151. Begin
  152. dest_32 := Pint32(dest);
  153. source_32 := Pint32(source);
  154. { If the current pixel isn't dword aligned, try write one pixel first }
  155. If (PtrUInt(dest_32) And $3) <> 0 Then
  156. Begin
  157. s_pixel := ((source_32^ Shr 8) And $f800) Or
  158. ((source_32^ Shr 5) And $7e0) Or
  159. ((source_32^ Shr 3) And $1f);
  160. Pshort16(dest_32)^ := s_pixel;
  161. dest_32 := Pint32(dest + 2);
  162. Inc(source_32);
  163. Dec(count);
  164. End;
  165. { Write blocks of two pixels }
  166. For i := 1 To count Shr 1 Do
  167. Begin
  168. {This horrible construct is actually faster than loading into a variable}
  169. dest_32^ := ((source_32^ Shr 8) And $f800) Or
  170. ((source_32^ Shr 5) And $7e0) Or
  171. ((source_32^ Shr 3) And $1f) Or
  172. (((source_32 + 1)^ Shl 8) And $f8000000) Or
  173. (((source_32 + 1)^ Shl 11) And $7e00000) Or
  174. (((source_32 + 1)^ Shl 13) And $1f0000);
  175. Inc(dest_32);
  176. Inc(source_32, 2);
  177. End;
  178. { Eventually, write a single odd pixel that might be left }
  179. If (count And 1) <> 0 Then
  180. Begin
  181. s_pixel := source_32^;
  182. Pshort16(dest_32)^ := ((s_pixel Shr 8) And $f800) Or
  183. ((s_pixel Shr 5) And $7e0) Or
  184. ((s_pixel Shr 3) And $1f);
  185. End;
  186. End;
  187. { TO 16 BGR 565 }
  188. Procedure ConvertP_32rgb888_16bgr565(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  189. Var
  190. i : DWord;
  191. r, g, b : int32;
  192. s_pixel, d_pixelblock : int32;
  193. d_pixel : short16;
  194. Begin
  195. { If the current pixel isn't dword aligned, try write one pixel first }
  196. If (PtrUInt(dest) And $3) <> 0 Then
  197. Begin
  198. s_pixel := Pint32(source)^;
  199. r := (s_pixel Shr 19) And $1f;
  200. g := (s_pixel Shr 5) And $7e0;
  201. b := (s_pixel Shl 8) And $f800;
  202. d_pixel := r Or g Or b;
  203. Pshort16(dest)^ := d_pixel;
  204. Inc(source, 4);
  205. Inc(dest, 2);
  206. Dec(count);
  207. End;
  208. { Write blocks of two pixels }
  209. For i := 1 To count Shr 1 Do
  210. Begin
  211. s_pixel := Pint32(source)^;
  212. d_pixelblock := ((s_pixel Shr 19) And $1f) Or
  213. ((s_pixel Shr 5) And $7e0) Or
  214. ((s_pixel Shl 8) And $f800);
  215. s_pixel := (Pint32(source) + 1)^;
  216. d_pixelblock := d_pixelblock Or
  217. ((((s_pixel Shr 19) And $1f) Or
  218. ((s_pixel Shr 5) And $7e0) Or
  219. ((s_pixel Shl 8) And $f800)) Shl 16);
  220. Pint32(dest)^ := d_pixelblock;
  221. Inc(source, 8);
  222. Inc(dest, 4);
  223. End;
  224. { Eventually, write a single odd pixel that might be left }
  225. If (count And 1) <> 0 Then
  226. Begin
  227. s_pixel := Pint32(source)^;
  228. r := (s_pixel Shr 19) And $1f;
  229. g := (s_pixel Shr 5) And $7e0;
  230. b := (s_pixel Shl 8) And $f800;
  231. d_pixel := r Or g Or b;
  232. Pshort16(dest)^ := d_pixel;
  233. End;
  234. End;
  235. { TO 16 RGB 555 }
  236. Procedure ConvertP_32rgb888_16rgb555(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  237. Var
  238. r, g, b : int32;
  239. s_pixel, d_pixelblock : int32;
  240. d_pixel : short16;
  241. i : DWord;
  242. Begin
  243. If (PtrUInt(dest) And $3) <> 0 Then
  244. Begin
  245. s_pixel := Pint32(source)^;
  246. r := (s_pixel Shr 9) And $7c00;
  247. g := (s_pixel Shr 6) And $3e0;
  248. b := (s_pixel Shr 3) And $1f;
  249. d_pixel := r Or g Or b;
  250. Pshort16(dest)^ := d_pixel;
  251. Inc(source, 4);
  252. Inc(dest, 2);
  253. Dec(count);
  254. End;
  255. For i := 1 To count Shr 1 Do
  256. Begin
  257. s_pixel := Pint32(source)^;
  258. d_pixelblock := ((s_pixel Shr 9) And $7c00) Or
  259. ((s_pixel Shr 6) And $3e0) Or
  260. ((s_pixel Shr 3) And $1f);
  261. s_pixel := (Pint32(source) + 1)^;
  262. d_pixelblock := d_pixelblock Or
  263. ((((s_pixel Shr 9) And $7c00) Or
  264. ((s_pixel Shr 6) And $3e0) Or
  265. ((s_pixel Shr 3) And $1f)) Shl 16);
  266. Pint32(dest)^ := d_pixelblock;
  267. Inc(source, 8);
  268. Inc(dest, 4);
  269. End;
  270. If (count And 1) <> 0 Then
  271. Begin
  272. s_pixel := Pint32(source)^;
  273. r := (s_pixel Shr 9) And $7c00;
  274. g := (s_pixel Shr 6) And $3e0;
  275. b := (s_pixel Shr 3) And $1f;
  276. d_pixel := r Or g Or b;
  277. Pshort16(dest)^ := d_pixel;
  278. End;
  279. End;
  280. { TO 16 BGR 555 }
  281. Procedure ConvertP_32rgb888_16bgr555(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  282. Var
  283. r, g, b : int32;
  284. s_pixel, d_pixelblock : int32;
  285. d_pixel : short16;
  286. i : DWord;
  287. Begin
  288. If (PtrUInt(dest) And $3) <> 0 Then
  289. Begin
  290. s_pixel := Pint32(source)^;
  291. r := (s_pixel Shr 19) And $1f;
  292. g := (s_pixel Shr 6) And $3e0;
  293. b := (s_pixel Shl 7) And $7c00;
  294. d_pixel := r Or g Or b;
  295. Pshort16(dest)^ := d_pixel;
  296. Inc(source, 4);
  297. Inc(dest, 2);
  298. Dec(count);
  299. End;
  300. For i := 1 To count Shr 1 Do
  301. Begin
  302. s_pixel := Pint32(source)^;
  303. d_pixelblock := ((s_pixel Shr 19) And $1f) Or
  304. ((s_pixel Shr 6) And $3e0) Or
  305. ((s_pixel Shl 7) And $7c00);
  306. s_pixel := (Pint32(source) + 1)^;
  307. d_pixelblock := d_pixelblock Or
  308. ((((s_pixel Shr 19) And $1f) Or
  309. ((s_pixel Shr 6) And $3e0) Or
  310. ((s_pixel Shl 7) And $7c00)) Shl 16);
  311. Pint32(dest)^ := d_pixelblock;
  312. Inc(source, 8);
  313. Inc(dest, 4);
  314. End;
  315. If (count And 1) <> 0 Then
  316. Begin
  317. s_pixel := Pint32(source)^;
  318. r := (s_pixel Shr 19) And $1f;
  319. g := (s_pixel Shr 6) And $3e0;
  320. b := (s_pixel Shl 7) And $7c00;
  321. d_pixel := r Or g Or b;
  322. Pshort16(dest)^ := d_pixel;
  323. End;
  324. End;
  325. { TO 8 RGB 332 }
  326. Procedure ConvertP_32rgb888_8rgb332(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  327. Var
  328. i : DWord;
  329. s_pixel, d_block : int32;
  330. d_pixel : char8;
  331. Begin
  332. { Process single pixels until we are dword aligned }
  333. While (PtrUInt(dest) And $3) <> 0 Do
  334. Begin
  335. s_pixel := Pint32(source)^;
  336. d_pixel := ((s_pixel Shr 16) And $e0) Or
  337. ((s_pixel Shr 11) And $1c) Or
  338. ((s_pixel Shr 6) And $3);
  339. dest^ := d_pixel;
  340. Dec(count);
  341. If count = 0 Then
  342. Exit;
  343. Inc(dest);
  344. Inc(source, 4);
  345. End;
  346. { Now process blocks of four pixels }
  347. For i := 1 To count Shr 2 Do
  348. Begin
  349. s_pixel := Pint32(source)^;
  350. d_block := ((s_pixel Shr 16) And $e0) Or
  351. ((s_pixel Shr 11) And $1c) Or
  352. ((s_pixel Shr 6) And $3);
  353. s_pixel := (Pint32(source) + 1)^;
  354. d_block := ((((s_pixel Shr 16) And $e0) Or
  355. ((s_pixel Shr 11) And $1c) Or
  356. ((s_pixel Shr 6) And $3)) Shl 8) Or d_block;
  357. s_pixel := (Pint32(source) + 2)^;
  358. d_block := ((((s_pixel Shr 16) And $e0) Or
  359. ((s_pixel Shr 11) And $1c) Or
  360. ((s_pixel Shr 6) And $3)) Shl 16) Or d_block;
  361. s_pixel := (Pint32(source) + 3)^;
  362. d_block := ((((s_pixel Shr 16) And $e0) Or
  363. ((s_pixel Shr 11) And $1c) Or
  364. ((s_pixel Shr 6) And $3)) Shl 24) Or d_block;
  365. Pint32(dest)^ := d_block;
  366. Inc(source, 16);
  367. Inc(dest, 4);
  368. End;
  369. { Write all possibly remaining pixel }
  370. count := count And $3;
  371. While count <> 0 Do
  372. Begin
  373. Dec(count);
  374. s_pixel := Pint32(source)^;
  375. dest^ := ((s_pixel Shr 16) And $e0) Or
  376. ((s_pixel Shr 11) And $1c) Or
  377. ((s_pixel Shr 6) And $3);
  378. Inc(dest);
  379. Inc(source, 4);
  380. End;
  381. End;
  382. { -------------------------------------------------------------------------
  383. STRETCH CONVERTERS
  384. ------------------------------------------------------------------------- }
  385. Procedure ConvertP_32rgb888_32bgr888_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  386. Var
  387. x : DWord;
  388. s_pixel : int32;
  389. s_ptr : Pchar8;
  390. tmp : char8;
  391. Begin
  392. x := 0;
  393. s_ptr := @s_pixel;
  394. Repeat
  395. s_pixel := (Pint32(source)+(x Shr 16))^;
  396. tmp := (s_ptr + R_32)^;
  397. (s_ptr + R_32)^ := (s_ptr + B_32)^;
  398. (s_ptr + B_32)^ := tmp;
  399. Pint32(dest)^ := s_pixel;
  400. Inc(dest, 4);
  401. Inc(x, inc_source);
  402. Dec(count);
  403. Until count = 0;
  404. End;
  405. Procedure ConvertP_32rgb888_32rgba888_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  406. Var
  407. x : DWord;
  408. Begin
  409. x := 0;
  410. Repeat
  411. Pint32(dest)^ := ((Pint32(source) + (x Shr 16))^ Shl 8) Or $ff;
  412. Inc(dest, 4);
  413. Inc(x, inc_source);
  414. Dec(count);
  415. Until count = 0;
  416. End;
  417. Procedure ConvertP_32rgb888_32bgra888_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  418. Var
  419. x : DWord;
  420. s_pixel : int32;
  421. s_ptr : Pchar8;
  422. tmp : char8;
  423. Begin
  424. x := 0;
  425. s_ptr := @s_pixel;
  426. Repeat
  427. s_pixel := (Pint32(source)+(x Shr 16))^;
  428. tmp := (s_ptr + R_32)^;
  429. (s_ptr + R_32)^ := (s_ptr + B_32)^;
  430. (s_ptr + B_32)^ := tmp;
  431. Pint32(dest)^ := (s_pixel Shl 8) Or $ff;
  432. Inc(dest, 4);
  433. Inc(x, inc_source);
  434. Dec(count);
  435. Until count = 0;
  436. End;
  437. Procedure ConvertP_32rgb888_24rgb888_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  438. Var
  439. x, c : DWord;
  440. s1, s2 : DWord;
  441. Begin
  442. x := 0;
  443. While (PtrUInt(dest) And 3) <> 0 Do
  444. Begin
  445. Pshort16(dest)^ := Pshort16(source)^;
  446. (dest + 2)^ := (source + 2)^;
  447. Inc(x, inc_source);
  448. Inc(source, (x Shr 16)*4);
  449. x := x And $FFFF;
  450. Inc(dest, 3);
  451. Dec(count);
  452. If count = 0 Then
  453. Exit;
  454. End;
  455. c := count Shr 2;
  456. While c > 0 Do
  457. Begin
  458. s1 := (Pint32(source) + ((x + inc_source) Shr 16))^ And $FFFFFF;
  459. Pint32(dest)^ := ((Pint32(source) + (x Shr 16))^ And $FFFFFF) Or (s1 Shl 24);
  460. s2 := (Pint32(source) + ((x + 2*inc_source) Shr 16))^ And $FFFFFF;
  461. Pint32(dest + 4)^ := (s1 Shr 8) Or (s2 Shl 16);
  462. Pint32(dest + 8)^ := (s2 Shr 16) Or ((Pint32(source) + ((x + 3*inc_source) Shr 16))^ Shl 8);
  463. Inc(x, 4*inc_source);
  464. Inc(dest, 12);
  465. Dec(c);
  466. End;
  467. Inc(source, (x Shr 16) * 4);
  468. x := x And $FFFF;
  469. count := count And $3;
  470. While count > 0 Do
  471. Begin
  472. Pshort16(dest)^ := Pshort16(source)^;
  473. (dest + 2)^ := (source + 2)^;
  474. Inc(x, inc_source);
  475. Inc(source, (x Shr 16)*4);
  476. x := x And $FFFF;
  477. Inc(dest, 3);
  478. Dec(count);
  479. End;
  480. End;
  481. Procedure ConvertP_32rgb888_24bgr888_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  482. Var
  483. x, c : DWord;
  484. s1, s2, s3, s4 : DWord;
  485. Begin
  486. x := 0;
  487. While (PtrUInt(dest) And 3) <> 0 Do
  488. Begin
  489. (dest)^ := (source + 2)^;
  490. (dest + 1)^ := (source + 1)^;
  491. (dest + 2)^ := (source)^;
  492. Inc(x, inc_source);
  493. Inc(source, (x Shr 16)*4);
  494. x := x And $FFFF;
  495. Inc(dest, 3);
  496. Dec(count);
  497. If count = 0 Then
  498. Exit;
  499. End;
  500. c := count Shr 2;
  501. While c > 0 Do
  502. Begin
  503. s1 := (Pint32(source) + (x Shr 16))^;
  504. s2 := (Pint32(source) + ((x + inc_source) Shr 16))^;
  505. s3 := (Pint32(source) + ((x + 2*inc_source) Shr 16))^;
  506. s4 := (Pint32(source) + ((x + 3*inc_source) Shr 16))^;
  507. Pint32(dest + 0)^ := ((s2 And $FF0000) Shl 8) Or ((s1 And $FF) Shl 16) Or (s1 And $FF00) Or ((s1 Shr 16) And $FF);
  508. Pint32(dest + 4)^ := ((s3 And $FF00) Shl 16) Or (s3 And $FF0000) Or ((s2 And $FF) Shl 8) Or ((s2 Shr 8) And $FF);
  509. Pint32(dest + 8)^ := ((s4 And $FF) Shl 24) Or ((s4 And $FF00) Shl 8) Or ((s4 Shr 8) And $FF00) Or (s3 And $FF);
  510. Inc(x, 4*inc_source);
  511. Inc(dest, 12);
  512. Dec(c);
  513. End;
  514. Inc(source, (x Shr 16) * 4);
  515. x := x And $FFFF;
  516. count := count And $3;
  517. While count > 0 Do
  518. Begin
  519. (dest)^ := (source + 2)^;
  520. (dest + 1)^ := (source + 1)^;
  521. (dest + 2)^ := (source)^;
  522. Inc(x, inc_source);
  523. Inc(source, (x Shr 16)*4);
  524. x := x And $FFFF;
  525. Inc(dest, 3);
  526. Dec(count);
  527. End;
  528. End;
  529. Procedure ConvertP_32rgb888_16rgb565_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  530. Var
  531. x, c : DWord;
  532. p : int32;
  533. Begin
  534. x := 0;
  535. { Align mod 4 }
  536. If (PtrUInt(dest) And 3) <> 0 Then
  537. Begin
  538. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 8) And $f800) Or
  539. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  540. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f);
  541. Inc(x, inc_source);
  542. Inc(dest, 2);
  543. Dec(count);
  544. End;
  545. { Try to write 2 pixel blocks }
  546. c := count Shr 1;
  547. While c <> 0 Do
  548. Begin
  549. Dec(c);
  550. p := (((Pint32(source) + (x Shr 16))^ Shr 8) And $f800) Or
  551. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  552. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f);
  553. Inc(x, inc_source);
  554. p := p Or
  555. (((((Pint32(source) + (x Shr 16))^ Shr 8) And $f800) Or
  556. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  557. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f)) Shl 16);
  558. Inc(x, inc_source);
  559. Pint32(dest)^ := p;
  560. Inc(dest, 4);
  561. End;
  562. { Write trailing pixel }
  563. If (count And 1) <> 0 Then
  564. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 8) And $f800) Or
  565. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  566. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f);
  567. End;
  568. Procedure ConvertP_32rgb888_16bgr565_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  569. Var
  570. x, c : DWord;
  571. p : int32;
  572. Begin
  573. x := 0;
  574. { Align mod 4 }
  575. If (PtrUInt(dest) And 3) <> 0 Then
  576. Begin
  577. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  578. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  579. (((Pint32(source) + (x Shr 16))^ Shl 8) And $f800);
  580. Inc(x, inc_source);
  581. Inc(dest, 2);
  582. Dec(count);
  583. End;
  584. { Try to write 2 pixel blocks }
  585. c := count Shr 1;
  586. While c <> 0 Do
  587. Begin
  588. Dec(c);
  589. p := (((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  590. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  591. (((Pint32(source) + (x Shr 16))^ Shl 8) And $f800);
  592. Inc(x, inc_source);
  593. p := p Or
  594. (((((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  595. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  596. (((Pint32(source) + (x Shr 16))^ Shl 8) And $f800)) Shl 16);
  597. Inc(x, inc_source);
  598. Pint32(dest)^ := p;
  599. Inc(dest, 4);
  600. End;
  601. { Write trailing pixel }
  602. If (count And 1) <> 0 Then
  603. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  604. (((Pint32(source) + (x Shr 16))^ Shr 5) And $7e0) Or
  605. (((Pint32(source) + (x Shr 16))^ Shl 8) And $f800);
  606. End;
  607. Procedure ConvertP_32rgb888_16rgb555_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  608. Var
  609. x, c : DWord;
  610. p : int32;
  611. Begin
  612. x := 0;
  613. { Align mod 4 }
  614. If (PtrUInt(dest) And 3) <> 0 Then
  615. Begin
  616. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 9) And $7c00) Or
  617. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  618. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f);
  619. Inc(x, inc_source);
  620. Inc(dest, 2);
  621. Dec(count);
  622. End;
  623. { Try to write 2 pixel blocks }
  624. c := count Shr 1;
  625. While c <> 0 Do
  626. Begin
  627. Dec(c);
  628. p := (((Pint32(source) + (x Shr 16))^ Shr 9) And $7c00) Or
  629. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  630. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f);
  631. Inc(x, inc_source);
  632. p := p Or
  633. (((((Pint32(source) + (x Shr 16))^ Shr 9) And $7c00) Or
  634. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  635. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f)) Shl 16);
  636. Inc(x, inc_source);
  637. Pint32(dest)^ := p;
  638. Inc(dest, 4);
  639. End;
  640. { Write trailing pixel }
  641. If (count And 1) <> 0 Then
  642. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 9) And $7c00) Or
  643. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  644. (((Pint32(source) + (x Shr 16))^ Shr 3) And $1f);
  645. End;
  646. Procedure ConvertP_32rgb888_16bgr555_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  647. Var
  648. x, c : DWord;
  649. p : int32;
  650. Begin
  651. x := 0;
  652. { Align mod 4 }
  653. If (PtrUInt(dest) And 3) <> 0 Then
  654. Begin
  655. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  656. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  657. (((Pint32(source) + (x Shr 16))^ Shl 7) And $7c00);
  658. Inc(x, inc_source);
  659. Inc(dest, 2);
  660. Dec(count);
  661. End;
  662. { Try to write 2 pixel blocks }
  663. c := count Shr 1;
  664. While c <> 0 Do
  665. Begin
  666. Dec(c);
  667. p := (((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  668. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  669. (((Pint32(source) + (x Shr 16))^ Shl 7) And $7c00);
  670. Inc(x, inc_source);
  671. p := p Or
  672. (((((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  673. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  674. (((Pint32(source) + (x Shr 16))^ Shl 7) And $7c00)) Shl 16);
  675. Inc(x, inc_source);
  676. Pint32(dest)^ := p;
  677. Inc(dest, 4);
  678. End;
  679. { Write trailing pixel }
  680. If (count And 1) <> 0 Then
  681. Pshort16(dest)^ := (((Pint32(source) + (x Shr 16))^ Shr 19) And $1f) Or
  682. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3e0) Or
  683. (((Pint32(source) + (x Shr 16))^ Shl 7) And $7c00);
  684. End;
  685. Procedure ConvertP_32rgb888_8rgb332_S(source, dest : Pchar8; count, inc_source : DWord); CDecl;
  686. Var
  687. x, c : DWord;
  688. p : int32;
  689. Begin
  690. x := 0;
  691. { Write single pixels until the destination address is aligned mod 4 }
  692. While (PtrUInt(dest) And $3) <> 0 Do
  693. Begin
  694. dest^ := (((Pint32(source) + (x Shr 16))^ Shr 16) And $e0) Or
  695. (((Pint32(source) + (x Shr 16))^ Shr 11) And $1c) Or
  696. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3);
  697. Inc(x, inc_source);
  698. Inc(dest);
  699. Dec(count);
  700. If count = 0 Then
  701. Exit;
  702. End;
  703. { Write blocks of four pixels now }
  704. c := count Shr 2;
  705. While c <> 0 Do
  706. Begin
  707. Dec(c);
  708. p := (((Pint32(source) + (x Shr 16))^ Shr 16) And $e0) Or
  709. (((Pint32(source) + (x Shr 16))^ Shr 11) And $1c) Or
  710. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3);
  711. Inc(x, inc_source);
  712. p := p Or
  713. (((((Pint32(source) + (x Shr 16))^ Shr 16) And $e0) Or
  714. (((Pint32(source) + (x Shr 16))^ Shr 11) And $1c) Or
  715. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3)) Shl 8);
  716. Inc(x, inc_source);
  717. p := p Or
  718. (((((Pint32(source) + (x Shr 16))^ Shr 16) And $e0) Or
  719. (((Pint32(source) + (x Shr 16))^ Shr 11) And $1c) Or
  720. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3)) Shl 16);
  721. Inc(x, inc_source);
  722. p := p Or
  723. (((((Pint32(source) + (x Shr 16))^ Shr 16) And $e0) Or
  724. (((Pint32(source) + (x Shr 16))^ Shr 11) And $1c) Or
  725. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3)) Shl 24);
  726. Inc(x, inc_source);
  727. Pint32(dest)^ := p;
  728. Inc(dest, 4);
  729. End;
  730. { Write up to three trailing pixels }
  731. c := count And $3;
  732. While c <> 0 Do
  733. Begin
  734. Dec(c);
  735. dest^ := (((Pint32(source) + (x Shr 16))^ Shr 16) And $e0) Or
  736. (((Pint32(source) + (x Shr 16))^ Shr 11) And $1c) Or
  737. (((Pint32(source) + (x Shr 16))^ Shr 6) And $3);
  738. Inc(x, inc_source);
  739. Inc(dest);
  740. End;
  741. End;