pal.cc 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285
  1. /********************************************************************** <BR>
  2. This file is part of Crack dot Com's free source code release of
  3. Golgotha. <a href="http://www.crack.com/golgotha_release"> <BR> for
  4. information about compiling & licensing issues visit this URL</a>
  5. <PRE> If that doesn't help, contact Jonathan Clark at
  6. golgotha_source@usa.net (Subject should have "GOLG" in it)
  7. ***********************************************************************/
  8. #include "palette/pal.hh"
  9. #include "math/num_type.hh"
  10. #include "memory/malloc.hh"
  11. #include "file/file.hh"
  12. #include <memory.h>
  13. i4_pal_manager_class i4_pal_man;
  14. int i4_lk_cmp_size[]={0,0,256*4, 16*4, 2*4};
  15. void i4_pixel_format::default_format()
  16. {
  17. red_mask = 0x00ff0000;
  18. green_mask = 0x0000ff00;
  19. blue_mask = 0x000000ff;
  20. alpha_mask = 0xff000000;
  21. calc_shift();
  22. lookup = 0;
  23. pixel_depth = I4_32BIT;
  24. }
  25. w32 i4_pixel_format::write(i4_file_class *f)
  26. {
  27. if (!f)
  28. return (13*4);
  29. f->write_32(red_mask);
  30. f->write_32(red_shift);
  31. f->write_32(red_bits);
  32. f->write_32(green_mask);
  33. f->write_32(green_shift);
  34. f->write_32(green_bits);
  35. f->write_32(blue_mask);
  36. f->write_32(blue_shift);
  37. f->write_32(blue_bits);
  38. f->write_32(alpha_mask);
  39. f->write_32(alpha_shift);
  40. f->write_32(alpha_bits);
  41. f->write_32(pixel_depth);
  42. return (13*4); //(# of bytes written)
  43. }
  44. void i4_pixel_format::read(i4_file_class *f)
  45. {
  46. red_mask = f->read_32();
  47. red_shift = f->read_32();
  48. red_bits = f->read_32();
  49. green_mask = f->read_32();
  50. green_shift = f->read_32();
  51. green_bits = f->read_32();
  52. blue_mask = f->read_32();
  53. blue_shift = f->read_32();
  54. blue_bits = f->read_32();
  55. alpha_mask = f->read_32();
  56. alpha_shift = f->read_32();
  57. alpha_bits = f->read_32();
  58. pixel_depth = (enum i4_pixel_depth)f->read_32();
  59. lookup = 0;
  60. }
  61. i4_bool i4_lookup_pal::can_convert(const i4_pixel_format *source_fmt,
  62. const i4_pixel_format *dest_fmt) const
  63. {
  64. return i4_T;
  65. }
  66. i4_color i4_lookup_pal::convert(const i4_color source_pixel,
  67. const i4_pixel_format *dest) const
  68. {
  69. w32 rgb=source.lookup[source_pixel];
  70. w32 r=((rgb>>16) & ((dest->red_mask>>dest->red_shift)<<(8-dest->red_bits)));
  71. w32 g=((rgb>>8) & ((dest->green_mask>>dest->green_shift)<<(8-dest->green_bits)));
  72. w32 b=((rgb>>0) & ((dest->blue_mask>>dest->blue_shift)<<(8-dest->blue_bits)));
  73. r = (r>>(8-dest->red_bits))<<dest->red_shift;
  74. g = (g>>(8-dest->green_bits))<<dest->green_shift;
  75. b = (b>>(8-dest->blue_bits))<<dest->blue_shift;
  76. return r|g|b;
  77. }
  78. i4_lookup_pal::i4_lookup_pal(i4_pixel_format *source_fmt)
  79. {
  80. source=*source_fmt;
  81. int size=i4_lk_cmp_size[source.pixel_depth];
  82. source.lookup = (w32 *)i4_malloc(size, "pal memory");
  83. memcpy(source.lookup, source_fmt->lookup, size);
  84. }
  85. i4_lookup_pal::~i4_lookup_pal()
  86. {
  87. i4_free(source.lookup);
  88. }
  89. i4_rgb_pal::i4_rgb_pal(i4_pixel_format *source_fmt)
  90. {
  91. source=*source_fmt;
  92. source.lookup=0;
  93. }
  94. i4_bool i4_rgb_pal::can_convert(const i4_pixel_format *source_fmt,
  95. const i4_pixel_format *dest_fmt) const
  96. {
  97. if ((source_fmt->pixel_depth == I4_32BIT ||
  98. source_fmt->pixel_depth == I4_16BIT) &&
  99. (dest_fmt->pixel_depth == I4_32BIT ||
  100. dest_fmt->pixel_depth == I4_16BIT))
  101. return i4_T;
  102. else
  103. return i4_F;
  104. }
  105. i4_color i4_rgb_pal::convert(const i4_color source_pixel,
  106. const i4_pixel_format *dest) const
  107. {
  108. w32 argb = source_pixel;
  109. w32 a = ((argb & source.alpha_mask)>>source.alpha_shift)<<(8-source.alpha_bits);
  110. w32 r = ((argb & source.red_mask)>>source.red_shift)<<(8-source.red_bits);
  111. w32 g = ((argb & source.green_mask)>>source.green_shift)<<(8-source.green_bits);
  112. w32 b = ((argb & source.blue_mask)>>source.blue_shift)<<(8-source.blue_bits);
  113. a = (a>>(8-dest->alpha_bits))<<dest->alpha_shift;
  114. r = (r>>(8-dest->red_bits))<<dest->red_shift;
  115. g = (g>>(8-dest->green_bits))<<dest->green_shift;
  116. b = (b>>(8-dest->blue_bits))<<dest->blue_shift;
  117. return a|r|g|b;
  118. }
  119. i4_pal *i4_pal_manager_class::register_pal(i4_pixel_format *format)
  120. {
  121. i4_pixel_format dest;
  122. dest.default_format();
  123. i4_pal *p;
  124. i4_isl_list<i4_pal>::iterator i;
  125. for (i=pal_list.begin(); i!=pal_list.end(); ++i)
  126. {
  127. if (format->pixel_depth == i->source.pixel_depth)
  128. {
  129. if (format->pixel_depth == I4_8BIT ||
  130. format->pixel_depth == I4_4BIT ||
  131. format->pixel_depth == I4_2BIT)
  132. {
  133. if (memcmp(format->lookup,
  134. i->source.lookup,
  135. i4_lk_cmp_size[format->pixel_depth])==0)
  136. {
  137. p=&(*i);
  138. return p;
  139. }
  140. } else if (format->red_mask == i->source.red_mask &&
  141. format->green_mask == i->source.green_mask &&
  142. format->blue_mask == i->source.blue_mask &&
  143. format->alpha_mask == i->source.alpha_mask)
  144. {
  145. p=&(*i);
  146. return p;
  147. }
  148. }
  149. }
  150. if (format->pixel_depth == I4_8BIT ||
  151. format->pixel_depth == I4_4BIT ||
  152. format->pixel_depth == I4_2BIT)
  153. {
  154. i4_lookup_pal *l= new i4_lookup_pal(format);
  155. pal_list.insert(*l);
  156. p=l;
  157. }
  158. else
  159. {
  160. i4_rgb_pal *l= new i4_rgb_pal(format);
  161. pal_list.insert(*l);
  162. p=l;
  163. }
  164. return p;
  165. }
  166. void i4_pal_manager_class::init()
  167. {
  168. i4_pixel_format d;
  169. d.default_format();
  170. def32=register_pal(&d);
  171. d.alpha_mask=0;
  172. d.calc_shift();
  173. def_na_32=register_pal(&d);
  174. w32 tmp[256];
  175. d.pixel_depth=I4_8BIT;
  176. d.lookup=tmp;
  177. def8=register_pal(&d);
  178. }
  179. void i4_pal_manager_class::uninit()
  180. {
  181. pal_list.destroy_all();
  182. }
  183. i4_color i4_pal_manager_class::convert_32_to(i4_color c,
  184. const i4_pixel_format *dest_format) const
  185. {
  186. return def32->convert(c, dest_format);
  187. }
  188. i4_color i4_pal_manager_class::convert_to_32(i4_color c, const i4_pal *source_format)
  189. const
  190. {
  191. return source_format->convert(c, &def32->source);
  192. }
  193. void i4_pixel_format::calc_shift()
  194. {
  195. w32 c;
  196. c=red_mask;
  197. for (red_shift=0; (c&1)==0; red_shift++, c=c>>1);
  198. for (red_bits=0; (c&1)==1; red_bits++, c=c>>1);
  199. c=green_mask;
  200. for (green_shift=0; (c&1)==0; green_shift++, c=c>>1);
  201. for (green_bits=0; (c&1)==1; green_bits++, c=c>>1);
  202. c=blue_mask;
  203. for (blue_shift=0; (c&1)==0; blue_shift++, c=c>>1);
  204. for (blue_bits=0; (c&1)==1; blue_bits++, c=c>>1);
  205. c=alpha_mask;
  206. for (alpha_shift=0; (c&1)==0 && alpha_shift<99; alpha_shift++, c=c>>1);
  207. if (alpha_shift==99) alpha_shift=0;
  208. for (alpha_bits=0; (c&1)==1 && alpha_bits<99; alpha_bits++, c=c>>1);
  209. if (alpha_bits==99) alpha_bits=0;
  210. }
  211. w32 g1_light_color(w32 color, float intensity)
  212. {
  213. float r=(color>>16)&0xff;
  214. float g=(color>>8)&0xff;
  215. float b=(color>>0)&0xff;
  216. r*=intensity;
  217. g*=intensity;
  218. b*=intensity;
  219. return ((i4_f_to_i(r)<<16) | (i4_f_to_i(g)<<8) | (i4_f_to_i(b)));
  220. }