軟件課程設(shè)計(jì)C語言實(shí)現(xiàn)BMP圖像顯示_第1頁
軟件課程設(shè)計(jì)C語言實(shí)現(xiàn)BMP圖像顯示_第2頁
軟件課程設(shè)計(jì)C語言實(shí)現(xiàn)BMP圖像顯示_第3頁
軟件課程設(shè)計(jì)C語言實(shí)現(xiàn)BMP圖像顯示_第4頁
軟件課程設(shè)計(jì)C語言實(shí)現(xiàn)BMP圖像顯示_第5頁
已閱讀5頁,還剩25頁未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

1、xx大學(xué)xx系課程設(shè)計(jì)報(bào)告(最終報(bào)告)( 2010 - 2011 年度第 2 學(xué)期)名 稱: 軟件課程設(shè)計(jì) 題 目:bmp圖象分析與顯示院 系: 班 級(jí): 學(xué) 號(hào): 學(xué)生姓名: 指導(dǎo)教師: 設(shè)計(jì)周數(shù): 15 成 績(jī): 日期: 2011 年 5 月 31 日目 錄1.設(shè)計(jì)任務(wù)12.基本思路23.方案設(shè)計(jì)23.1 主要算法說明23.2 程序框架設(shè)計(jì)94.程序的部分源代碼分析及介紹145.調(diào)試過程中出現(xiàn)的問題及相應(yīng)解決辦法186.個(gè)人體會(huì)及建議267.參考文獻(xiàn)27 1. 設(shè)計(jì)任務(wù)1.1利用c語言實(shí)現(xiàn)bmp格式圖象文件的分析和顯示。主要內(nèi)容包括: a)基本任務(wù):完成bmp格式圖像的顯示,要求在提供的畫

2、布上循環(huán)的顯示某一文件夾下面所有的bmp文件(支持所有bmp格式); b)拓展任務(wù):實(shí)現(xiàn)圖像的特效顯示(淡入淡出,百頁窗等等)。 1.2進(jìn)度情況: a、我對(duì)bmp圖像的了解bmp 文件是標(biāo)準(zhǔn)的windows位圖文件,有16色、256色、16位真彩色及24位 真彩色等格式。客觀存在按文件頭、圖像控制信息、彩色表和位圖點(diǎn)陣數(shù)據(jù)的格式來存儲(chǔ)。文件頭是定義圖像文件的類型、長度等的數(shù)據(jù)結(jié)構(gòu):圖像控制信息是定義圖像顏色格式、圖像大小、顏色數(shù)等的數(shù)據(jù)結(jié)構(gòu):彩色表是定義圖像顏色的調(diào)色板的數(shù)組位圖點(diǎn)陣,是定義圖像數(shù)據(jù)的數(shù)組。未經(jīng)壓縮的bmp文件中,位圖點(diǎn)陣信息是按掃描線從下至上(bottom to top)存儲(chǔ)

3、的,即圖像的第一個(gè)像素值在位圖陣列的左下角,最后一個(gè)像素值在位圖陣列的右上角。對(duì)16色位圖,每個(gè)像素占4位,每個(gè)字節(jié)存放相鄰的兩個(gè)像素值,高4位存放的第1個(gè)像素值在掃描線的前面,低4位存放的第2個(gè)像素值在掃描線后面。對(duì)256色位圖,1個(gè)字節(jié)存放1個(gè)像素值。對(duì)24位位圖,顏色表為空,位圖數(shù)據(jù)的每3個(gè)字節(jié)對(duì)應(yīng)1個(gè)像素值,其中每個(gè)字節(jié)分別對(duì)應(yīng)該像素值的p、r、g值。b、我對(duì)于bmp圖像顯示平臺(tái)的理解1、通過enum來對(duì)各個(gè)按鍵(向上,向下,向左右等)作出定義2、定義結(jié)構(gòu)體t_message,用于接收和發(fā)出信號(hào),來控制各個(gè)函數(shù)的進(jìn)度。3、創(chuàng)建消息隊(duì)列,用于控制各個(gè)程序的進(jìn)度(即決定什么時(shí)候開始或者結(jié)束

4、它的進(jìn)程)4、定義結(jié)構(gòu)體變量t_messagerecvmsg,用于接收從隊(duì)列中發(fā)出的消息。5、利用函數(shù)dtos_drv_receivemessage( test_queueid, &recvmsg),根據(jù)其中recvmsg.param0的數(shù)值來決定是否進(jìn)行這個(gè)進(jìn)度。若recvmsg.param0等于msg_keyright,則進(jìn)行圖像顯示程序,獲取圖像名稱,調(diào)用圖像顯示函數(shù),對(duì)圖像進(jìn)行分析和顯示;否則跳出循環(huán)。c、已能夠正確顯示32bit,24bit,1bit,4bit(未壓縮),8bit(未壓縮),4bit(壓縮),8bit(壓縮),16bit(1555模式,565模式,4444模式)的圖像

5、。2. 基本思路通過查閱資料和自己的思考,猜想,我覺得要實(shí)現(xiàn)在畫布上顯示bmp圖像,主要有以下幾種方法 最初的想法是可以利用描點(diǎn)函數(shù)gfmsetpixels,逐個(gè)顯示出bmp圖像的點(diǎn),最終構(gòu)成一幅完整的圖像。具體編碼后,證實(shí)這是可行的。 查閱一些資料后,我了解到還可以利用粘貼函數(shù)gfmwriterectangle。即將圖像文件中的數(shù)據(jù)讀取出來,用malloc動(dòng)態(tài)分配內(nèi)存,記錄圖像數(shù)據(jù),然后將內(nèi)存中數(shù)據(jù)拷貝到畫布上的一個(gè)矩形框內(nèi),即實(shí)現(xiàn)了圖像的顯示。但是繼續(xù)研究之后發(fā)現(xiàn),這個(gè)方法涉及到將1,4,8,16,24bit圖像數(shù)據(jù)修改為32bit的問題,比較復(fù)雜,所以最終還是采用了方案。3. 方案設(shè)計(jì)3

6、.1 主要算法說明:主要方法:將不同像素的圖像分別用不同的函數(shù)實(shí)現(xiàn),即分別定義show1bit,show4bit,show32bit等幾個(gè)函數(shù),再定義函數(shù)showbmp,按照需要顯示的圖像像素,決定調(diào)用相應(yīng)的圖像顯示函數(shù)。這么做可以使結(jié)構(gòu)比較清晰,增強(qiáng)代碼的可讀性。具體實(shí)現(xiàn)方法:定義信息頭結(jié)構(gòu)變量(其中變量包含bmp圖像的文件頭和信息頭:文件標(biāo)識(shí)“bm”,文件大小,保留位,數(shù)據(jù)偏移,信息頭長度,寬度,高度,面數(shù),像素的位數(shù),壓縮類型,位圖數(shù)據(jù)大小,水平分辨率,垂直分辨率,顏色數(shù),重要顏色)定義函數(shù),讀取文件頭和信息頭定義各個(gè)像素bmp圖像的顯示函數(shù) 32bit bmp圖像的顯示函數(shù) 定義文件指

7、針 用fopen打開圖像文件 利用fseek函數(shù)將文件內(nèi)部指針移到位圖數(shù)據(jù)區(qū),跳過信息頭部分 用fread函數(shù)將顏色信息讀取出來,存放在int32u型的變量color中 調(diào)用畫點(diǎn)函數(shù)gfmsetpixels,把color中的顏色信息顯示在畫布上 利用雙重循環(huán),依次逐行讀取顏色信息,顯示在畫布上 顯示結(jié)束,用fclose關(guān)閉文件 24bit bmp圖像的顯示函數(shù) 由于24bit圖像和32bit圖像一樣,都沒用調(diào)色板,所以實(shí)現(xiàn)過程相似,但有一點(diǎn)不同: 因?yàn)?4bit的顏色信息占據(jù)3個(gè)字節(jié),而32bit的顏色信息為4個(gè)字節(jié),故利用fread函數(shù)讀取顏色信息時(shí),參數(shù)有所不同。 32bit:fread(

8、&color,4,1,fp); 24bit:fread(&color,3,1,fp): 8bit未壓縮bmp圖像的顯示函數(shù) 由于8bit圖像有調(diào)色板,故應(yīng)當(dāng)先定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時(shí),將數(shù)據(jù)對(duì)應(yīng)的調(diào)色板顏色找出來,作為gfmsetpixels的顏色參數(shù),描出一個(gè)點(diǎn)。 定義文件指針 定義存放調(diào)色板顏色數(shù)據(jù)的數(shù)組colorboard256,定義循環(huán)變量i,j和顏色變量color等用fopen打開圖像文件 利用fseek函數(shù)將文件內(nèi)部指針移到調(diào)色板數(shù)據(jù)區(qū),跳過信息頭部分 使用for循環(huán),調(diào)用fread函數(shù)讀出調(diào)色板數(shù)據(jù)放入數(shù)組colorboard256中:fread(&col

9、orboardi,4,1,fp); 注意用rewind(fp)重新定位指針到文件首部 重新使用fseek函數(shù)跳過信息頭和調(diào)色板數(shù)據(jù) fseek(fp,point-remove,0); 雙重循環(huán),依次讀出位圖數(shù)據(jù)。這里1字節(jié)的數(shù)據(jù)對(duì)應(yīng)調(diào)色板中的一個(gè)顏色,所以用fread時(shí)數(shù)據(jù)長度的參數(shù)應(yīng)當(dāng)設(shè)為1。 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1;j+) fread(&pcolor,1,1,fp);/讀取一個(gè)位圖數(shù)據(jù) color=colorboardpcolor&0xff;/取讀出的數(shù)據(jù)的一位,對(duì)應(yīng)到調(diào)色板的一個(gè)顏色 if(jbmpwidth)gfmsetpi

10、xels(color,j,point-bmpheight-i,1); 顯示結(jié)束,用fclose關(guān)閉文件 4bit未壓縮bmp圖像的顯示函數(shù) 4bit圖像也有調(diào)色板,也應(yīng)當(dāng)先定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時(shí),將數(shù)據(jù)對(duì)應(yīng)的調(diào)色板顏色找出來,作為gfmsetpixels的顏色參數(shù),描出一個(gè)點(diǎn)。但是和8bit圖像略有不同的是,位圖數(shù)據(jù)的4bit對(duì)應(yīng)了調(diào)色板中的一個(gè)顏色數(shù)據(jù),而不正好是1個(gè)字節(jié),故應(yīng)當(dāng)對(duì)取出的位圖數(shù)據(jù)做一些處理。 定義文件指針 定義存放調(diào)色板顏色數(shù)據(jù)的數(shù)組colorboard16,定義循環(huán)變量i,j和顏色變量color等用fopen打開圖像文件 利用fseek函數(shù)將文件內(nèi)

11、部指針移到調(diào)色板數(shù)據(jù)區(qū),跳過信息頭部分 使用for循環(huán),調(diào)用fread函數(shù)讀出調(diào)色板數(shù)據(jù)放入數(shù)組colorboard16中:fread(&colorboardi,4,1,fp); 注意用rewind(fp)重新定位指針到文件首部 重新使用fseek函數(shù)跳過信息頭和調(diào)色板數(shù)據(jù) fseek(fp,point-remove,0); 雙重循環(huán),依次讀出位圖數(shù)據(jù)。這里1/2字節(jié)(即4bit)的數(shù)據(jù)對(duì)應(yīng)調(diào)色板中的一個(gè)顏色,所以應(yīng)當(dāng)把得到的位圖數(shù)據(jù)拆成前后兩部分,分別對(duì)應(yīng)到調(diào)色板中的一種顏色。為了取得前面的4bit,使用二進(jìn)制右移運(yùn)算符,把不需要的4bit移出;為取得后面的4bit,使用按位與運(yùn)算符&,把前

12、面的4bit置零。 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1;j+) fread(&pcolor,1,1,fp);/讀取一個(gè)位圖數(shù)據(jù) pcolor41=pcolor4&0x0f;/取出數(shù)據(jù)的前面4bit color=colorboardpcolor41;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色 if(jbmpwidth)gfmsetpixels(color,2*j,point-bmpheight-i,1); pcolor42=pcolor&0x0f;/取出數(shù)據(jù)的后面4bit color=colorboardpcolor42;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色 if(jbmpw

13、idth)gfmsetpixels(color,2*j+1,point-bmpheight-i,1); 顯示結(jié)束,用fclose關(guān)閉文件 1bit bmp圖像的顯示函數(shù) 1bit圖像也有調(diào)色板,也應(yīng)當(dāng)先定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時(shí),將數(shù)據(jù)對(duì)應(yīng)的調(diào)色板顏色找出來,作為gfmsetpixels的顏色參數(shù),描出一個(gè)點(diǎn)。但是它位圖數(shù)據(jù)的1bit對(duì)應(yīng)了調(diào)色板中的一個(gè)顏色數(shù)據(jù),不正好是1個(gè)字節(jié),故也應(yīng)當(dāng)對(duì)取出的位圖數(shù)據(jù)做一些處理。 定義文件指針 定義存放調(diào)色板顏色數(shù)據(jù)的數(shù)組colorboard2,定義循環(huán)變量i,j和顏色變量color等用fopen打開圖像文件 利用fseek函數(shù)將文件

14、內(nèi)部指針移到調(diào)色板數(shù)據(jù)區(qū),跳過信息頭部分 使用for循環(huán),調(diào)用fread函數(shù)讀出調(diào)色板數(shù)據(jù)放入數(shù)組colorboard2中:fread(&colorboardi,4,1,fp); 注意用rewind(fp)重新定位指針到文件首部 重新使用fseek函數(shù)跳過信息頭和調(diào)色板數(shù)據(jù) fseek(fp,point-remove,0); 雙重循環(huán),依次讀出位圖數(shù)據(jù)。這里1/8字節(jié)(即1bit)的數(shù)據(jù)對(duì)應(yīng)調(diào)色板中的一個(gè)顏色,所以應(yīng)當(dāng)按位將數(shù)據(jù)取出,分別對(duì)應(yīng)調(diào)色板中的一個(gè)顏色數(shù)據(jù)??紤]再使用一重循環(huán),每次把位圖數(shù)據(jù)移動(dòng)一位,取得每個(gè)位的數(shù)據(jù)。內(nèi)層取位循環(huán)如下:for(k=0;k(7-k)&0x01;/取讀出的

15、數(shù)據(jù)的一位color=colorboardpcolor1;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色if(jbmpwidth)gfmsetpixels(color,8*j+k,point-bmpheight-i,1); 顯示結(jié)束,用fclose關(guān)閉文件 vi 8bit 壓縮bmp圖像的顯示函數(shù) 壓縮算法:行程壓縮編碼的編碼方式:由2個(gè)字節(jié)組成,第一個(gè)字節(jié)指定象素?cái)?shù)目,第二個(gè)字節(jié)定義顏色索引,當(dāng)?shù)谝粋€(gè)字節(jié)置零時(shí),聯(lián)合使用第二個(gè)字節(jié)中的值表示: 第二個(gè)字節(jié)的值為0:行的結(jié)束。 第二個(gè)字節(jié)的值為1:圖象結(jié)束。 第二個(gè)字節(jié)的值為2:其后的兩個(gè)字節(jié)表示下一個(gè)象素從當(dāng)前開始的水平和垂直位置的偏移量。這個(gè)字節(jié)對(duì)中的第一個(gè)字節(jié)

16、設(shè)置為0,第二個(gè)字節(jié)包含有顏色索引數(shù),其后續(xù)字節(jié)包含有顏色索引。故程序算法如下: 定義文件指針 定義存放調(diào)色板顏色數(shù)據(jù)的數(shù)組colorboard216,定義循環(huán)變量i,j,內(nèi)部循環(huán)變量a,定義相同顏色數(shù)目和顏色索引顏色變量colornum, samecolor,行列偏移量iremove, jremove,對(duì)應(yīng)到調(diào)色板顏色的數(shù)據(jù)pcolor和顏色變量color等(由于后面要對(duì)一個(gè)字節(jié)的數(shù)據(jù)進(jìn)行判斷,注意要把a(bǔ),colornum,samecolor,iremove,jremove,pcolor設(shè)置成int8u型,占一個(gè)字節(jié)并且無符號(hào)) 用fopen打開圖像文件 利用fseek函數(shù)將文件內(nèi)部指針移到

17、調(diào)色板數(shù)據(jù)區(qū),跳過信息頭部分 使用for循環(huán),調(diào)用fread函數(shù)讀出調(diào)色板數(shù)據(jù)放入數(shù)組colorboard216中:fread(&colorboardi,4,1,fp); 注意用rewind(fp)重新定位指針到文件首部 重新使用fseek函數(shù)跳過信息頭和調(diào)色板數(shù)據(jù) 讀取第一個(gè)相同顏色數(shù)的數(shù)據(jù)colornum,判斷若不為0,轉(zhuǎn);若colornum為0,轉(zhuǎn) 若colornum不為零,后一字節(jié)表示顏色索引,讀取samecolor,將它對(duì)應(yīng)到調(diào)色板:color=colorboardsamecolor; 利用for循環(huán)畫出colornum個(gè)點(diǎn)。 若colornum為零,聯(lián)合第二個(gè)字節(jié)判斷。讀取第二個(gè)字

18、節(jié)samecolor,若第二個(gè)字節(jié)為0,表示行結(jié)束,令行數(shù)加1,列變量置零;若第二個(gè)字節(jié)為1,表示rle編碼圖像結(jié)束,用break退出循環(huán);若第二個(gè)字節(jié)為2,其后的兩個(gè)字節(jié)表示下一個(gè)象素從當(dāng)前開始的水平和垂直位置的偏移量,用fread讀取行列偏移量,把行列分別加上這兩個(gè)數(shù)據(jù);若第二個(gè)字節(jié)大于2,則第二個(gè)字節(jié)表示其后有效的顏色數(shù)據(jù),利用for循環(huán),設(shè)置條件為asamecolor,畫出解壓縮以后的點(diǎn)。 顯示結(jié)束,用fclose關(guān)閉文件 vii 4bit 壓縮bmp圖像的顯示函數(shù) 算法基本與8bit壓縮圖像一致,稍有不同如下:顏色索引數(shù)據(jù)samecolor(一個(gè)字節(jié))分為兩部分,高四位和低四位分別對(duì)

19、應(yīng)兩個(gè)調(diào)色板中的顏色。相同顏色數(shù)colornum的第一個(gè)對(duì)應(yīng)高四位,第二個(gè)對(duì)應(yīng)低四位,第三個(gè)對(duì)應(yīng)高四位,以此循環(huán)。 viii 16bit bmp圖像的顯示函數(shù) 16bit圖像有1555,4444,565三種模式。分別代表用于表示圖像顏色數(shù)據(jù)的2字節(jié)(16bit)中rgb的值。1555中1代表混合參數(shù),后面三個(gè)5分別表示rgb的值;4444中第一個(gè)4代表混合參數(shù),后面三個(gè)4分別表示rgb的值; 565中5、6、5分別表示rgb的值?;痉椒ㄊ抢梦贿\(yùn)算,分別得出不同模式下的rgb值,并對(duì)它們作出調(diào)整,使得rgb值都占一個(gè)字節(jié),得出最終的顏色值。最后利用描點(diǎn)函數(shù)gfmsetpixels畫出處理過的

20、顏色點(diǎn)。1 定義文件指針2 定義用于判斷565和4444模式的變量a3 用fopen打開圖像文件4 判斷壓縮類型bmprletype,若bmprletype值為0,轉(zhuǎn);若bmprletype值不為0,轉(zhuǎn)5 bmprletype=0,表示圖像為1555模式。紅色的掩碼為(0111110000000000)2,即0x7c00;綠的掩碼為(0000001111100000)2,即0x03e0;藍(lán)的掩碼為(0000000000011111)2,即0x001f。利用按位與運(yùn)算得出rgb的值。r值原位于11位,經(jīng)調(diào)整后,應(yīng)當(dāng)位于20位,故應(yīng)該把按位與之后的結(jié)果左移9位。g、b值類似。三者相加得出最終顏色r

21、gbcolor。代碼如下:rgbcolor=(color&0x7c00)9)+(color&0x03e0)6)+(color&0x001f)bmpheight-i,1);6 bmprletype不為零,利用a值進(jìn)行判斷。fread讀取a的值fread(&a,4,1,fp);判斷a值若為0xf800,則為565模式,轉(zhuǎn);若a值不為0xf800;為4444模式,轉(zhuǎn)7 a=0xf800,表示圖像為為565模式。紅色的掩碼為(1111100000000000)2,即0xf800;綠的掩碼為(0000011111100000)2,即0x07e0;藍(lán)的掩碼為(0000000000011111)2,即0x0

22、01f。利用按位與運(yùn)算得出rgb的值。移位方法與相似。三者相加得出最終顏色rgbcolor。代碼如下:rgbcolor=(color&0xf800)8)+(color&0x07e0)5)+(color&0x001f)3);利用描點(diǎn)函數(shù)畫出點(diǎn)8 a!=0xf800,表示圖像為為4444模式。紅色的掩碼為(0000111100000000)2,即0x0f00;綠的掩碼為(0000000111110000)2,即0x00f0;藍(lán)的掩碼為(0000000000001111)2,即0x000f。利用按位與運(yùn)算得出rgb的值。移位方法與相似。三者相加得出最終顏色rgbcolor。代碼如下:rgbcolor

23、=(color&0x0f00)12)+(color&0x00f0)8)+(color&0x000f)2第二個(gè)字節(jié)表示其后有效的顏色數(shù)據(jù)相同顏色數(shù)目不為零,后一字節(jié)表示顏色索引讀取顏色索引數(shù)據(jù)samecolor描點(diǎn)函數(shù)畫出點(diǎn) v 三種模式16bit圖像(1555,444,565)顯示流程開始打開圖像文件,跳過信息頭數(shù)據(jù),fread讀取調(diào)色板顏色信息,存入數(shù)組讀取用于判斷565和4444的數(shù)據(jù)a壓縮類型bmprletype=?y結(jié)束bmprletype=0a= 0xf800?利用位運(yùn)算得出顏色數(shù)據(jù)的rgb值,再根據(jù)不同模式的算法進(jìn)行調(diào)整得出顏色變量n1555模式bmprletype =3565模式

24、描點(diǎn)函數(shù)畫出點(diǎn)4444模式4. 程序的部分源代碼分析及介紹4.1 主要顯示函數(shù)showbmpvoid showbmp(char *filename)/圖像顯示函數(shù) file * fp; struct filehead point; readhead(filename,&point);/調(diào)用頭信息讀取函數(shù)獲得圖像頭信息 if(fp=fopen(filename,rb)=null) printf(can not open); exit(1); switch(point.bmppix)/判斷圖像的顏色像素,決定使用哪個(gè)圖像顯示函數(shù) case 1:/若像素為1,調(diào)用1bit圖像顯示函數(shù) show1bi

25、t(filename,&point);break; /其余調(diào)用類似,這里省略關(guān)鍵是利用圖像信息頭中的bmppix(像素位數(shù))來判斷應(yīng)當(dāng)調(diào)用哪個(gè)圖像顯示函數(shù)4.2 32bit圖像顯示函數(shù)void show32bit(char*filename,struct filehead* point)/顯示32bit圖像的函數(shù) file*fp; int32u color; int32u i,j; if(fp=fopen(filename,rb)=null) printf(can not open the file!); exit(1); fseek(fp,point-remove,0);/跳過文件頭信息頭數(shù)

26、據(jù)區(qū) for(i=0;ibmpheight;i+) for(j=0;jbmpwidth;j+) fread(&color,4,1,fp);/每次讀取4個(gè)字節(jié)(即32bit)的數(shù)據(jù) gfmsetpixels(color,j,point-bmpheight-i,1); fclose(fp);關(guān)鍵是用fseek跳過信息頭,還有注意bmp圖像讀取時(shí)是從左下角開始的。 24bit圖像顯示函數(shù)與32bit基本一樣,在第三部分已做過說明,這里不再贅述。4.3 8bit圖像顯示函數(shù)void show8bit(char*filename,struct filehead* point) file*fp; int3

27、2u color,pcolor; int32u i,j; int32u colorboard256;/存放調(diào)色板數(shù)據(jù)的數(shù)組 if(fp=fopen(filename,rb)=null) printf(can not open the file!); exit(1); fseek(fp,0x36,0); for(i=0;iremove,0);/跳過信息頭和調(diào)色板 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1;j+) fread(&pcolor,1,1,fp);/讀取一個(gè)位圖數(shù)據(jù) color=colorboardpcolor&0xff;/取讀出的數(shù)據(jù)的一位,

28、對(duì)應(yīng)到調(diào)色板的一個(gè)顏色 if(jbmpwidth)gfmsetpixels(color,j,point-bmpheight-i,1); 關(guān)鍵是定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時(shí)對(duì)應(yīng)到調(diào)色板中的顏色。4bit顯示函數(shù)與8bit思路一致,但要注意有位運(yùn)算。fread(&pcolor,1,1,fp);/讀取一個(gè)位圖數(shù)據(jù)pcolor41=pcolor4&0x0f;/取出數(shù)據(jù)的前面4bitcolor=colorboardpcolor41;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色if(jbmpwidth) gfmsetpixels(color,2*j,point-bmpheight-i,1);pcolor4

29、2=pcolor&0x0f;/取出數(shù)據(jù)的后面4bitcolor=colorboardpcolor42;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色if(jbmpwidth) gfmsetpixels(color,2*j+1,point-bmpheight-i,1);1bit圖像顯示類似。4.4 8bit(壓縮)圖像顯示函數(shù)void show8rlebit(char*filename,struct filehead* point)/相同部分省略 int8u colornum,samecolor, iremove,jremove, pcolor;/定義相同顏色數(shù)目,顏色索引,行列偏移量等/讀取調(diào)色板數(shù)據(jù)與未壓縮的一樣

30、,這里省略j=0;for(i=0;ibmpheight;)fread(&colornum,1,1,fp);/讀取第一個(gè)相同顏色數(shù)的數(shù)據(jù)if(colornum=0)/判斷若為0,聯(lián)合第二個(gè)字節(jié)判斷fread(&samecolor,1,1,fp);/讀取第二個(gè)字節(jié)if(samecolor=0)/第二個(gè)字節(jié)為0,表示行結(jié)束i+;j=0;else if(samecolor=1)/第二個(gè)字節(jié)為1,表示rle編碼圖像結(jié)束break;else if(samecolor=2)/*第二個(gè)字節(jié)為2,其后的兩個(gè)字節(jié)表示下一個(gè)象素從當(dāng)前開始的水平和垂直位置的偏移量*/fread(&jremove,1,1,fp);fr

31、ead(&iremove,1,1,fp);i+=iremove;j+=jremove;else/若第二個(gè)字節(jié)大于2,則第二個(gè)字節(jié)表示其后有效的顏色數(shù)據(jù) for(a=0;abmpheight-i,1);/畫出解壓縮以后的點(diǎn)j+;if(samecolor%2!=0) /若samecolor為奇數(shù),再讀取一個(gè)字節(jié)、fread(&pcolor,1,1,fp);else/相同顏色數(shù)目不為零,后一字節(jié)表示顏色索引fread(&samecolor,1,1,fp);/讀取顏色索引數(shù)據(jù) for(a=0;abmpheight-i,1);j+;fclose(fp);4bit壓縮與8bit類似,不同點(diǎn)如下:for(a

32、=0;asamecolor;a+)if(a%2=0)/a為偶數(shù),即第1,3,5,個(gè)顏色,對(duì)應(yīng)高四位顏色 fread(&pcolor,1,1,fp); pcolor1=(pcolor&0xf0)bmpheight-i,1);/畫出解壓縮以后的點(diǎn) j+; else/第2,4,6個(gè)顏色對(duì)應(yīng)低四位 color2=colorboardpcolor2; gfmsetpixels(color2,j,point-bmpheight-i,1); j+; if(samecolor%4=1|samecolor%4=2)fread(&pcolor,1,1,fp);4.5 16bit(1555,4444,565模式)圖

33、像顯示函數(shù)void show16bit(char*filename,struct filehead* point)/定義各種變量,打開文件等,與前面類似,這里省略 fseek(fp,point-remove,0); if(point-bmprletype=0)/1555類型 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1);j+) fread(&color,2,1,fp);/讀取2個(gè)字節(jié)的顏色數(shù)據(jù)rgbcolor=(color&0x7c00)9)+(color&0x03e0)6)+(color&0x001f)bmpheight-i,1); else if(

34、point-bmprletype=3) fread(&a,4,1,fp); fseek(fp,12,seek_cur); if(a=0xf800)/565類型 /與1555類似,不同點(diǎn)在于rgb掩碼以及處理方式: rgbcolor=(color&0xf800)8)+(color&0x07e0)5)+(color&0x001f)3); else if(a!=0xf800)/4444類型 /與1555類似,不同點(diǎn)在于rgb掩碼以及處理方式:、rgbcolor=(color&0x0f00)12)+(color&0x00f0)8)+(color&0x000f)remove,0); 或者fseek(fp

35、,54,0);這樣就解決了問題 問題二 問題:編寫的32bit圖像顯示函數(shù)調(diào)試運(yùn)行后出現(xiàn)如下結(jié)果(下圖) 問題原因分析:由顯示可知,圖像的上下顛倒,可能是使用描點(diǎn)函數(shù)gfmsetpixels時(shí),參數(shù)y弄錯(cuò)了。而由本文1.2可知,位圖點(diǎn)陣信息是按掃描線從下至上(bottom to top)存儲(chǔ)的,即圖像的第一個(gè)像素值在位圖陣列的左下角,最后一個(gè)像素值在位圖陣列的右上角。 解決方法:原來的繪圖函數(shù)為 gfmsetpixels(color,j, i,1); 將它改為gfmsetpixels(color,j,point-bmpheight-i,1);這樣就解決了問題。 問題三問題:編寫的24bit圖像

36、顯示函數(shù)調(diào)試運(yùn)行后出現(xiàn)如下結(jié)果(下圖)問題原因分析:請(qǐng)教老師之后得知,在讀取圖像時(shí),所有圖像的像素寬度都應(yīng)當(dāng)是4的倍數(shù),而這幅24bit圖像的大小為711*533,而寬度711*3=2133不能被4整除解決方法:可以利用如下算法,把任意一張圖片的寬度調(diào)整為4的倍數(shù):(width*3) 1行有效的字節(jié)數(shù);(width*3)%4 被4除余數(shù)是多少4-(width*3)%4 需要補(bǔ)充的字節(jié)數(shù)(4-(width*3)%4)%4 width*3如果是4的倍數(shù),那么上面的計(jì)算結(jié)果等于4,在對(duì)4取余,得到的就是每一行填充的字節(jié)數(shù)。patch = (4-(width*3)%4)%4;for(i=0;iheig

37、ht;i+) for(j=0;jwidth;j+) fread(&color, 3, 1, fp); gfmsetpixels(color, j, i, 1); fseek(fp, patch, seek_cur);對(duì)于16bit的圖片,patch=(4-(width*2)%4)%4;對(duì)于8bit的圖片,patch=(4-(width)%4)%4;對(duì)于4bit的圖片,patch=(8-(width*2)%8)%8;對(duì)于1bit的圖片,patch=(32-(width*32)%32)%32; 問題四 問題:編寫的8bit圖像顯示函數(shù)調(diào)試后無法運(yùn)行,運(yùn)行時(shí)顯示“vc已經(jīng)停止工作” 問題原因分析:可

38、能是處理位圖數(shù)據(jù)對(duì)應(yīng)到調(diào)色板時(shí)出現(xiàn)了一些問題。int32u為4個(gè)字節(jié),位圖數(shù)據(jù)只有1個(gè)字節(jié),計(jì)算機(jī)自動(dòng)賦值c,表示不定,這時(shí)應(yīng)當(dāng)給前面的字節(jié)賦值0。 解決方法:原來內(nèi)層循環(huán)中的代碼為fread(&pcolor,1,1,fp);/讀取一個(gè)位圖數(shù)據(jù)color=colorboardpcolor;/取讀出的數(shù)據(jù)的一位,對(duì)應(yīng)到調(diào)色板的一個(gè)顏色if(jbmpwidth)gfmsetpixels(color,j,point-bmpheight-i,1);將其中的數(shù)據(jù)對(duì)應(yīng)到調(diào)色板中的代碼改為 color=colorboardpcolor&0xff;就解決了問題。 問題五 問題:編寫的4bit圖像顯示函數(shù)調(diào)試運(yùn)

39、行后出現(xiàn)如下結(jié)果(下圖) 問題原因分析:由顯示可知,顯示的寬度變?yōu)樵瓉淼?倍,高度變?yōu)樵瓉淼?/2,應(yīng)當(dāng)是循環(huán)變量的范圍有錯(cuò)誤。 解決方法:應(yīng)當(dāng)將原來循環(huán)變量的范圍改為1/2。原來的代碼 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1;j+) fread(&pcolor,1,1,fp);/讀取一個(gè)位圖數(shù)據(jù) pcolor41=pcolor4&0x0f;/取出數(shù)據(jù)的前面4bit color=colorboardpcolor41;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色 gfmsetpixels(color,2*j,point-bmpheight-i,1); pcolor42=

40、pcolor&0x0f;/取出數(shù)據(jù)的后面4bit color=colorboardpcolor42;/對(duì)應(yīng)到調(diào)色板的一個(gè)顏色 gfmsetpixels(color,2*j+1,point-bmpheight-i,1); 將for(j=0;jbmpwidth+1;j+)改為for(j=0;jbmpwidth+1)/2;j+)即可解決問題。 問題六 問題:編寫的1bit圖像顯示函數(shù)調(diào)試運(yùn)行后出現(xiàn)如下結(jié)果(下圖) 問題原因分析:在對(duì)圖像寬度進(jìn)行處理之后,顯示出了原來不存在的點(diǎn),所以應(yīng)當(dāng)在顯示點(diǎn)的時(shí)候,加上一個(gè)條件限制,使得不屬于原本圖像的點(diǎn)不顯示出來。 解決方法:原來循環(huán)中寬度處理的算法為jbmpw

41、idth+11)/8顯示的時(shí)候應(yīng)當(dāng)加上限制條件if(jbmpwidth/8),使得加上的11不顯示出來。但是這樣會(huì)使得圖片缺少右邊的一條。原因是bmpwidth/8有小數(shù)被舍去,內(nèi)層循環(huán)的時(shí)候,有些點(diǎn)沒有畫出。應(yīng)當(dāng)改為:jbmpwidth+7-k)/8;vii 問題七 問題:編寫的4bit(壓縮)圖像顯示函數(shù)顯示如下 問題原因分析:圖像中出現(xiàn)了黑色的條紋,應(yīng)該是高低4位的顏色中有一位出現(xiàn)了錯(cuò)誤。 解決方法:原來顏色處理代碼為:pcolor1=(pcolor4)&0x0f;就解決了問題。viii 問題八 問題:編寫的16bit(1555)圖像顯示函數(shù)顯示如下 問題原因分析:右邊邊緣多處了一條線,顯示了多余的數(shù)據(jù)。 解決方法:在寬度顯示時(shí),加上一個(gè)寬度限制,超過寬度bmpwidth,就不用顯示了:if(jbmpwidth)gfmsetpixels(rgbcolor,j,point-bmpheight-i,1);這樣就解決了問題。ix 問題九 問題:編寫的16bit

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

最新文檔

評(píng)論

0/150

提交評(píng)論