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

下載本文檔

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

文檔簡介

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

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

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

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

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

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

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

8、&color,4,1,fp); 24bit:fread(&color,3,1,fp): 8bit未壓縮bmp圖像的顯示函數(shù) 由于8bit圖像有調(diào)色板,故應(yīng)當先定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時,將數(shù)據(jù)對應(yīng)的調(diào)色板顏色找出來,作為gfmsetpixels的顏色參數(shù),描出一個點。 定義文件指針 定義存放調(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ù)對應(yīng)調(diào)色板中的一個顏色,所以用fread時數(shù)據(jù)長度的參數(shù)應(yīng)當設(shè)為1。 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1;j+) fread(&pcolor,1,1,fp);/讀取一個位圖數(shù)據(jù) color=colorboardpcolor&0xff;/取讀出的數(shù)據(jù)的一位,對應(yīng)到調(diào)色板的一個顏色 if(jbmpwidth)gfmsetpi

10、xels(color,j,point-bmpheight-i,1); 顯示結(jié)束,用fclose關(guān)閉文件 4bit未壓縮bmp圖像的顯示函數(shù) 4bit圖像也有調(diào)色板,也應(yīng)當先定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時,將數(shù)據(jù)對應(yīng)的調(diào)色板顏色找出來,作為gfmsetpixels的顏色參數(shù),描出一個點。但是和8bit圖像略有不同的是,位圖數(shù)據(jù)的4bit對應(yīng)了調(diào)色板中的一個顏色數(shù)據(jù),而不正好是1個字節(jié),故應(yīng)當對取出的位圖數(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ù)對應(yīng)調(diào)色板中的一個顏色,所以應(yīng)當把得到的位圖數(shù)據(jù)拆成前后兩部分,分別對應(yīng)到調(diào)色板中的一種顏色。為了取得前面的4bit,使用二進制右移運算符,把不需要的4bit移出;為取得后面的4bit,使用按位與運算符&,把前

12、面的4bit置零。 for(i=0;ibmpheight;i+) for(j=0;jbmpwidth+1;j+) fread(&pcolor,1,1,fp);/讀取一個位圖數(shù)據(jù) pcolor41=pcolor4&0x0f;/取出數(shù)據(jù)的前面4bit color=colorboardpcolor41;/對應(yīng)到調(diào)色板的一個顏色 if(jbmpwidth)gfmsetpixels(color,2*j,point-bmpheight-i,1); pcolor42=pcolor&0x0f;/取出數(shù)據(jù)的后面4bit color=colorboardpcolor42;/對應(yīng)到調(diào)色板的一個顏色 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)當先定義數(shù)組來存放調(diào)色板的數(shù)據(jù),然后在讀取位圖數(shù)據(jù)時,將數(shù)據(jù)對應(yīng)的調(diào)色板顏色找出來,作為gfmsetpixels的顏色參數(shù),描出一個點。但是它位圖數(shù)據(jù)的1bit對應(yīng)了調(diào)色板中的一個顏色數(shù)據(jù),不正好是1個字節(jié),故也應(yīng)當對取出的位圖數(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ù)對應(yīng)調(diào)色板中的一個顏色,所以應(yīng)當按位將數(shù)據(jù)取出,分別對應(yīng)調(diào)色板中的一個顏色數(shù)據(jù)??紤]再使用一重循環(huán),每次把位圖數(shù)據(jù)移動一位,取得每個位的數(shù)據(jù)。內(nèi)層取位循環(huán)如下:for(k=0;k(7-k)&0x01;/取讀出的

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

16、設(shè)置為0,第二個字節(jié)包含有顏色索引數(shù),其后續(xù)字節(jié)包含有顏色索引。故程序算法如下: 定義文件指針 定義存放調(diào)色板顏色數(shù)據(jù)的數(shù)組colorboard216,定義循環(huán)變量i,j,內(nèi)部循環(huán)變量a,定義相同顏色數(shù)目和顏色索引顏色變量colornum, samecolor,行列偏移量iremove, jremove,對應(yīng)到調(diào)色板顏色的數(shù)據(jù)pcolor和顏色變量color等(由于后面要對一個字節(jié)的數(shù)據(jù)進行判斷,注意要把a,colornum,samecolor,iremove,jremove,pcolor設(shè)置成int8u型,占一個字節(jié)并且無符號) 用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ù) 讀取第一個相同顏色數(shù)的數(shù)據(jù)colornum,判斷若不為0,轉(zhuǎn);若colornum為0,轉(zhuǎn) 若colornum不為零,后一字節(jié)表示顏色索引,讀取samecolor,將它對應(yīng)到調(diào)色板:color=colorboardsamecolor; 利用for循環(huán)畫出colornum個點。 若colornum為零,聯(lián)合第二個字節(jié)判斷。讀取第二個字

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

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

20、顏色點。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;藍的掩碼為(0000000000011111)2,即0x001f。利用按位與運算得出rgb的值。r值原位于11位,經(jīng)調(diào)整后,應(yī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值進行判斷。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;藍的掩碼為(0000000000011111)2,即0x0

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

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

24、描點函數(shù)畫出點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)/判斷圖像的顏色像素,決定使用哪個圖像顯示函數(shù) case 1:/若像素為1,調(diào)用1bit圖像顯示函數(shù) show1bi

25、t(filename,&point);break; /其余調(diào)用類似,這里省略關(guān)鍵是利用圖像信息頭中的bmppix(像素位數(shù))來判斷應(yīng)當調(diào)用哪個圖像顯示函數(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個字節(jié)(即32bit)的數(shù)據(jù) gfmsetpixels(color,j,point-bmpheight-i,1); fclose(fp);關(guān)鍵是用fseek跳過信息頭,還有注意bmp圖像讀取時是從左下角開始的。 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);/讀取一個位圖數(shù)據(jù) color=colorboardpcolor&0xff;/取讀出的數(shù)據(jù)的一位,

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

29、2=pcolor&0x0f;/取出數(shù)據(jù)的后面4bitcolor=colorboardpcolor42;/對應(yīng)到調(diào)色板的一個顏色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);/讀取第一個相同顏色數(shù)的數(shù)據(jù)if(colornum=0)/判斷若為0,聯(lián)合第二個字節(jié)判斷fread(&samecolor,1,1,fp);/讀取第二個字節(jié)if(samecolor=0)/第二個字節(jié)為0,表示行結(jié)束i+;j=0;else if(samecolor=1)/第二個字節(jié)為1,表示rle編碼圖像結(jié)束break;else if(samecolor=2)/*第二個字節(jié)為2,其后的兩個字節(jié)表示下一個象素從當前開始的水平和垂直位置的偏移量*/fread(&jremove,1,1,fp);fr

31、ead(&iremove,1,1,fp);i+=iremove;j+=jremove;else/若第二個字節(jié)大于2,則第二個字節(jié)表示其后有效的顏色數(shù)據(jù) for(a=0;abmpheight-i,1);/畫出解壓縮以后的點j+;if(samecolor%2!=0) /若samecolor為奇數(shù),再讀取一個字節(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類似,不同點如下:for(a

32、=0;asamecolor;a+)if(a%2=0)/a為偶數(shù),即第1,3,5,個顏色,對應(yīng)高四位顏色 fread(&pcolor,1,1,fp); pcolor1=(pcolor&0xf0)bmpheight-i,1);/畫出解壓縮以后的點 j+; else/第2,4,6個顏色對應(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個字節(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類似,不同點在于rgb掩碼以及處理方式: rgbcolor=(color&0xf800)8)+(color&0x07e0)5)+(color&0x001f)3); else if(a!=0xf800)/4444類型 /與1555類似,不同點在于rgb掩碼以及處理方式:、rgbcolor=(color&0x0f00)12)+(color&0x00f0)8)+(color&0x000f)remove,0); 或者fseek(fp

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

36、顯示函數(shù)調(diào)試運行后出現(xiàn)如下結(jié)果(下圖)問題原因分析:請教老師之后得知,在讀取圖像時,所有圖像的像素寬度都應(yī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 需要補充的字節(jié)數(shù)(4-(width*3)%4)%4 width*3如果是4的倍數(shù),那么上面的計算結(jié)果等于4,在對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);對于16bit的圖片,patch=(4-(width*2)%4)%4;對于8bit的圖片,patch=(4-(width)%4)%4;對于4bit的圖片,patch=(8-(width*2)%8)%8;對于1bit的圖片,patch=(32-(width*32)%32)%32; 問題四 問題:編寫的8bit圖像顯示函數(shù)調(diào)試后無法運行,運行時顯示“vc已經(jīng)停止工作” 問題原因分析:可

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

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

40、pcolor&0x0f;/取出數(shù)據(jù)的后面4bit color=colorboardpcolor42;/對應(yīng)到調(diào)色板的一個顏色 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)試運行后出現(xiàn)如下結(jié)果(下圖) 問題原因分析:在對圖像寬度進行處理之后,顯示出了原來不存在的點,所以應(yīng)當在顯示點的時候,加上一個條件限制,使得不屬于原本圖像的點不顯示出來。 解決方法:原來循環(huán)中寬度處理的算法為jbmpw

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

溫馨提示

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

評論

0/150

提交評論