ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

c – 从给定的图像数据中提取像素数据.需要帮助了解代码

2019-08-30 02:08:26  阅读:257  来源: 互联网

标签:c bit-manipulation image-processing bit-shift


我一直在研究从图像数据构建纹理,但是一些教程提供的代码处理移位比特以获得图像像素.但是我对比特转换很新.我理解二进制&和|,但我不知道为什么需要此代码来获取像素数据.

这是纹理数据:

static char* g_pTextureData =
  "?VE`8U)K13Y:1C];2$%:5DQA>'&!@WB*:UQR9EET9%ES8UAP9UMZ>&%[A6Z$>6-Z"
  "S[6XR[*PIH2\"IXN0HY2>DWR#VL;+TL3,LYZ<QZVNUL\"_L)..NJJXN:>[V<#)R;\"Y"
  "W\\G,Y-/4P9^3SZ^KZ-K>RJN?S:VMY=/4U[NPW<+![-GCV<\"UX,C&Y-7BZ=K>V\\2^"
  "W\\F^XL[!R*.6UK:PYM7/RZB:U[R^V;^POY:)SZ^:Y]#/Y=')SZ^:Y]#/Y=')UKBH"
  "OY*%O9*%K()WPYF+Q)Z+JGUVU[RUO9.\"HW=MN9)\\R)N)MXQVM9!WRIN+QIJ+L8-W"
  "GG9FJGYNIGMMJ'YMK()PHWIKN9J+HX)GGGI?L8YQL8US@653F7EBJGYJJGUIEVU@"
  "GGY:F7E9E'18G'I9G'M:E'1;CW->C')6AVE3E'==F7ED<UQ5@6M4EWE5F7Y6DG92"
  "C'!6AVI5@613AVQ5B6U5@6=6?FA8?F96>V)5@6E6AVY<:UE6:UM1>V90@6E0@6A0"
  "<U]7=E]7<UE6<%M7=F!7<%M5:5=4:5M7;EI6:UM2;EY29%138E53:UA1:5A0<%]2"
  "9%E6<%U:;EE;;EA::UE79E548E%39%15:5957U)29E=58E-69EA6<%Y6<%Y6:5E5"
  "6U)3:UY<=F5A<U]?=F1>:UI:9EA7:5E78E158E-6;EQ89E=69%54:5M6<V189%E6"
  "4$I/7556;F->;F!?;EY>:UI=;EY=<&%=9%588E-59%55<&!;:5A96TY25DY/5D]0"
  "/SQ*03],1D-/2$523$)44$-65DI76TY86TQ674Y674Y49EA::5E;64Y2/SQ(/CQ("
  ",#%'+C!',#))-#-,-S--.3-./#9//#9./#1-0SM02D%013U,/SA*-S-(+BY%,3!&"
  "(R-%&Q]$&A]%'B)'(R1()\"5((B-(*2=(*\"9)+\"E)+2M))21%(\"%#'!Y#(\"%$(B)%"
  "\"A)\"\"A)\"\"1-\"\"A-\"\"A1\"\"A-\"\"Q-\"#!5\"#A5\"#A5\"#Q9\"$AA"
  "\"&QU$%QM#\"Q-\"\"A-\""
  "";

提供的宏用于获取颜色的位数据表示:

#define HEADER_PIXEL(data,pixel) { \
  pixel[0] = (((data[0] - 33) << 2) | ((data[1] - 33) >> 4)); \
  pixel[1] = ((((data[1] - 33) & 0xF) << 4) | ((data[2] - 33) >> 2)); \
  pixel[2] = ((((data[2] - 33) & 0x3) << 6) | ((data[3] - 33))); \
  data += 4; \
}

我的理解是’?’将有一个十进制值63.
所以跟随宏观,63 – 33 = 30
然后左移2位

(00000000 00000000 00000000 00011110) << 2
(00000000 00000000 00000000 01111000) = 120

接下来是V,十进制值为86
随着宏,86 – 33 = 53
然后右移4位

(00000000 00000000 00000000 00110101) >> 4
(00000000 00000000 00000000 00001101) = 13

然后我们做一个按位或操作

01111000
00001101
========
01111101 = 125

我理解这背后的数学.但我的问题是为什么需要数学?为什么33和位移?另外,为什么我们需要0xF和0x3?

它是否正在解压缩图像数据?或者它正在做其他事情?

这是我需要知道的吗?或者这只是一个非常具体的实例,因为这是我们压缩/解压缩图像的方式?

更新,谢谢@ v154c1,帮助我把它放进包里.

对于遇到此事的其他人.这就是我使用@ v154c1演示的方式使其合理化的方式.

00rrrrrr << 2 = rrrrrr00
00rrgggg >> 4 = 000000rr
rrrrrr00 | 000000rr = rrrrrrrr

00rrgggg & 00001111 = 0000gggg << 4 = gggg0000
00ggggbb & >> 2 = 0000gggg
gggg0000 | 0000gggg = gggggggg

00ggggbb & 00000011 = 000000bb << 6 = bb000000
00bbbbbb
bb000000 | 00bbbbbb = bbbbbbbb

解决方法:

Roger Rowland(Explanation of Header Pixel in GIMP created C Header File of an XPM image)的答案实际上解释得非常好.
它们以4个可打印字符存储RGB值(24位).

魔术值33是他们使用的第一个可打印字符(!为ASCII).

所以GIMP完成的过程是:

首先,您有一个像素,其中R,G和B为3个8位值.您可以像这样成像:

rrrrrrrr gggggggg bbbbbbbb

但是你不能简单地将它转储到头文件中.所以你将它分成6位组:(值0 – 63):

rrrrrr rrgggg ggggbb bbbbbb

然后将33添加到每个组(因此值为33 – 96.)然后将其作为4个字符存储到头文件中.

为了将其解码回像素数据,您只需减去33以获得原始的6位值,并将它们再次组合成3个8位值.

这种移位和掩模(&)简单地将这些位组合在一起.

例如,抓住第一个:

pixel[0] = (((data[0] - 33) << 2) | ((data[1] - 33) >> 4));

data [0]和data [1]是第一个和第二个字符(添加了33个).
所以你减去它(数据[0] – 33)并得到:

data[0] - 33 = rrrrrr
data[1] - 33 = rrgggg

然后轮班将价值推向正确的位置:

rrrrrr << 2  = rrrrrr00
rrgggg >> 4  =       rr

将它们一起添加时,您的原始值为rrrrrrrr.

值33到96映射到字符:

!, ", #, $, %, &, \', (, ), *, +, ,, -, ., /, 0, 1, 2, 3, 4, 5, 6, 7, 8,
9, :, ;, <, =, >, ?, @, A, B, C, D, E, F, G, H, I, J, K, L, M, N, O, P,
Q, R, S, T, U, V, W, X, Y, Z, [, \\, ], ^, _, `

标签:c,bit-manipulation,image-processing,bit-shift
来源: https://codeday.me/bug/20190830/1765048.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有