首页 >后端开发 >php教程 >PHP仿GD生成BMP图片

PHP仿GD生成BMP图片

WBOY
WBOY原创
2016-07-25 09:02:101240浏览
PHP仿GD生成BMP图片
  1. function imagebmp(&$im, $filename = '', $bit = 8, $compression = 0)
  2. {
  3. if (!in_array($bit, array(1, 4, 8, 16, 24, 32)))
  4. {
  5. $bit = 8;
  6. }
  7. else if ($bit == 32) // todo:32 bit
  8. {
  9. $bit = 24;
  10. }
  11. $bits = pow(2, $bit);
  12. // 调整调色板
  13. imagetruecolortopalette($im, true, $bits);
  14. $width = imagesx($im);
  15. $height = imagesy($im);
  16. $colors_num = imagecolorstotal($im);
  17. if ($bit {
  18. // 颜色索引
  19. $rgb_quad = '';
  20. for ($i = 0; $i {
  21. $colors = imagecolorsforindex($im, $i);
  22. $rgb_quad .= chr($colors['blue']) . chr($colors['green']) . chr($colors['red']) . "\0";
  23. }
  24. // 位图数据
  25. $bmp_data = '';
  26. // 非压缩
  27. if ($compression == 0 || $bit {
  28. if (!in_array($bit, array(1, 4, 8)))
  29. {
  30. $bit = 8;
  31. }
  32. $compression = 0;
  33. // 每行字节数必须为4的倍数,补齐。
  34. $extra = '';
  35. $padding = 4 - ceil($width / (8 / $bit)) % 4;
  36. if ($padding % 4 != 0)
  37. {
  38. $extra = str_repeat("\0", $padding);
  39. }
  40. for ($j = $height - 1; $j >= 0; $j --)
  41. {
  42. $i = 0;
  43. while ($i {
  44. $bin = 0;
  45. $limit = $width - $i
  46. for ($k = 8 - $bit; $k >= $limit; $k -= $bit)
  47. {
  48. $index = imagecolorat($im, $i, $j);
  49. $bin |= $index $i ++;
  50. }
  51. $bmp_data .= chr($bin);
  52. }
  53. $bmp_data .= $extra;
  54. }
  55. }
  56. // RLE8 压缩
  57. else if ($compression == 1 && $bit == 8)
  58. {
  59. for ($j = $height - 1; $j >= 0; $j --)
  60. {
  61. $last_index = "\0";
  62. $same_num = 0;
  63. for ($i = 0; $i {
  64. $index = imagecolorat($im, $i, $j);
  65. if ($index !== $last_index || $same_num > 255)
  66. {
  67. if ($same_num != 0)
  68. {
  69. $bmp_data .= chr($same_num) . chr($last_index);
  70. }
  71. $last_index = $index;
  72. $same_num = 1;
  73. }
  74. else
  75. {
  76. $same_num ++;
  77. }
  78. }
  79. $bmp_data .= "\0\0";
  80. }
  81. $bmp_data .= "\0\1";
  82. }
  83. $size_quad = strlen($rgb_quad);
  84. $size_data = strlen($bmp_data);
  85. }
  86. else
  87. {
  88. // 每行字节数必须为4的倍数,补齐。
  89. $extra = '';
  90. $padding = 4 - ($width * ($bit / 8)) % 4;
  91. if ($padding % 4 != 0)
  92. {
  93. $extra = str_repeat("\0", $padding);
  94. }
  95. // 位图数据
  96. $bmp_data = '';
  97. for ($j = $height - 1; $j >= 0; $j --)
  98. {
  99. for ($i = 0; $i {
  100. $index = imagecolorat($im, $i, $j);
  101. $colors = imagecolorsforindex($im, $index);
  102. if ($bit == 16)
  103. {
  104. $bin = 0
  105. $bin |= ($colors['red'] >> 3) $bin |= ($colors['green'] >> 3) $bin |= $colors['blue'] >> 3;
  106. $bmp_data .= pack("v", $bin);
  107. }
  108. else
  109. {
  110. $bmp_data .= pack("c*", $colors['blue'], $colors['green'], $colors['red']);
  111. }
  112. // todo: 32bit;
  113. }
  114. $bmp_data .= $extra;
  115. }
  116. $size_quad = 0;
  117. $size_data = strlen($bmp_data);
  118. $colors_num = 0;
  119. }
  120. // 位图文件头
  121. $file_header = "BM" . pack("V3", 54 + $size_quad + $size_data, 0, 54 + $size_quad);
  122. // 位图信息头
  123. $info_header = pack("V3v2V*", 0x28, $width, $height, 1, $bit, $compression, $size_data, 0, 0, $colors_num, 0);
  124. // 写入文件
  125. if ($filename != '')
  126. {
  127. $fp = fopen($filename, "wb");
  128. fwrite($fp, $file_header);
  129. fwrite($fp, $info_header);
  130. fwrite($fp, $rgb_quad);
  131. fwrite($fp, $bmp_data);
  132. fclose($fp);
  133. return true;
  134. }
  135. // 浏览器输出
  136. header("Content-Type: image/bmp");
  137. echo $file_header . $info_header;
  138. echo $rgb_quad;
  139. echo $bmp_data;
  140. return true;
  141. }
复制代码


声明:
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn