




版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領
文檔簡介
第
頁
北京郵電大學
基于Matlab的MIMO通信系統仿真
班 級:
姓 名:
學 號:
日 期:
目錄
TOC\o"1-3"\h\u
一、概述 3
(1)課設目的 3
(2)數字通信系統概述 3
二、基本原理
3
(1)MIMO系統理論
3
(2)MIMO系統模型 4
(3)分集與復用
4
三、仿真設計 7
(1)流程圖 7
(2)主要模塊 8
(3)主要參數 11
四、程序塊設計 11
(1)結構性和關鍵語句 11
信源產生 11
信道編碼 11
調制 11
MIMO信道模型 12
(2)狀態檢驗和性能測試 13
信源產生 13
調制 14
MIMO信道模型仿真 17
五、不同仿真條件下測試誤碼性能 18
六、仿真結果與分析 19
七、重點研究問題 19
八、結論(心得體會) 20
九、參考文獻 20
概述
課設目的
本課程設計的目的是了解移動通信關鍵技術、了解數字通信系統仿真流程,學會用Matlab實現基本的信道編譯碼、調制解調等通信模塊。學習并實現MIMO空時處理技術,通過本次實踐學習和掌握性能分析的思路和方法。
(2)數字通信系統概述
信道中傳輸的是數字信號的通信方式稱為數字通信,它包括將基帶數字信號直接送往信道傳輸的數字基帶傳輸和經載波調制后在送往信道傳輸的數字載波傳輸。對應的通信系統稱為數字通信系統。具體的通信流程如上圖所示。數字通信具有如下特點:抗特點干擾能力強,無噪聲積累;保密性能好;便于組成現代化數字通信網,便于實現多媒體通信和占用信道頻帶寬。
基本原理
MIMO系統理論:
MIMO(Multiple-InputMultiple-Out-put)表示多輸入多輸出。
MIMO的優點是能夠增加無線范圍并提高性能。MIMO允許多個天線同時發送和接收多個空間流。它允許天線同時傳送和接收。利用MIMO技術可以提高信道的容量,同時也可以提高信道的可靠性,降低誤碼率。前者是利用MIMO信道提供的空間復用增益,后者是利用MIMO信道提供的空間分集增益。
核心思想:時間上空時信號處理和空間上分集相結合。
時間上空時:通過在發送端采用空時碼實現,如空時分組、空時格碼,分層空時碼。
空間上分集:通過增加空間上天線分布實現。可以把原來對用戶來說是有害的無電波多徑傳播轉變為對用戶有利。
MIMO系統模型:
代表發送天線,代表接收天線。
信道矩陣:
接收矢量:,即接收信號為信道衰落系數發射信號+接收端噪聲
從上圖可以看到,MIMO模型中有一個空時編碼器,有多根天線,其系統模型和上述MIMO系統理論一致。發送天線的數目要大于接收天線,因為一般來說,移動終端所支持的天線數目總是比基站端要少。
分集與復用:
根據各根天線上發送信息的差別,MIMO可以分為發射分集技術和空間復用技術。
發射分集:在不同的天線上發射包含同樣信息的信號(信號的具體形式不一定完全相同),達到空間分集的效果,起到抗衰落的作用
典型代表:空時塊碼(STBC)
空間復用:在不同的天線上發射不同的信息,獲得空間復用增益,從而大大提高系統的容量和頻譜利用率
典型代表:分層空時碼
空時塊碼(STBC)
Alamouti提出了采用兩個發射天線和一個接收天線的系統可以得到采用一個發射天線兩個接收天線系統同樣的分集增益。
將每個輸入字符映射為一個矩陣,矩陣的每行對應在個不同的時間間隔里不同天線上所發送的符號。
在此例中,信源發送的二進制信息比特首先進行星座映射。假設采用4進制的調制星座,有。將從信源來的二進制信息比特,每2比特分為一組(此例中是x1和x2),對連續的兩組比特進行星座映射,得到兩個調制符號x1,x2。把這兩個符號送入編碼器,并按照如下方式編碼:
在第一個發送時刻,符號在天線1上發送出去,符號在天線2上發送出去。第二個時刻,符號在天線1上發送出去,符號在天線2上發送出去。可以看出,兩幅發送天線上發送信號批次存在著一定的關系,因此這種空時碼是基于發送分集的。兩幅發送天線上發送的信號滿足正交特性。
考慮兩個發送天線,一個接收天線的情況:
假設接收端可以完全準確地估計出信道的衰落系數和,在接收端采用最大似然估計,從星座中找出一對符號,該符號即最終接收端認為發送端發送的符號。在程序中,其判決式為:
其中,是根據信道衰落系數和接收信號進行合并得到的信號。
考慮多接收天線的情況:
多天線系統中,發送端的編碼與傳輸方案和單接收天線系統一樣。只是在接收端的處理變得復雜,需要對不同接收天線上接收到的信號進行合并處理。多接收天線下的判決度量可以通過把各副接收天線上的接受信號得到的判決度量線性合并得到。判決式如下:
分層空時碼(BLAST)
空時編碼利用多天線組成的天線陣同時發送和接收。在發送端,將數據流分離成多個支流,對每個支流進行空時處理和信號設計(空時編碼),然后通過不同天線同時發送;在接收端,利用天線陣接收,并經過空時處理和空時碼解碼,還原成發送數據流。
串并變換
信道編碼器1
信道編碼器2
空時編碼
調制器1
調制器2
天線1
天線n
圖1分層空時碼的發射端系統模型
在接收端,用多個天線分集接收,信道參數通過信道估計獲得,由線性判決反饋均衡器實現分層判決反饋干擾抵消,然后進行分層空時譯碼,單個信道譯碼器完成信道譯碼,分層空時碼接收端系統框圖如下圖所示:
信道估計
線性判決反饋均衡器
空時譯碼
信道譯碼
天線1
天線2
圖2分層空時碼的接收端系統模型
最后的系統結構圖:
仿真設計
流程圖
利用ML準則進行判決
解調,進行維特比譯碼
結束
主要模塊
信源產生
要求:產生獨立等概二進制信源
Matlab函數:randsrc()
信道編碼
利用卷積碼來進行信道編碼
根據3GPPTS36.212的規定,可選取如上所示的卷積碼來進行信道編碼。
卷積碼
卷積碼與分組碼不同,其編碼器具有記憶性,即編碼器的當前輸出不僅與當前輸入有關,還跟以前時刻的輸入有關。速率R=k/n、存儲器階數為m的卷積編碼器可用k個輸入、n個輸出、輸入存儲器階數為m的線性序貫電路實現,即輸入在進入編碼器后仍會多存儲m個時間單元。通常,n和k都是比較小的整數,k<n,信息序列被分成長度為k的分組,碼字被分成長度為n的分組。當k=1時,信息序列無需分組,處理連續進行。值得注意的是,卷積碼不像分組碼,較大的最小距離和低錯誤概率不是通過增加k和n實現的,而是通過增加存儲器階數m實現的。
卷積碼的編碼分為兩類:前饋和反饋。
卷積碼的譯碼可以分成兩大類:代數譯碼的門限譯碼、概率譯碼的序列譯碼與維特比譯碼。在該數字通信系統中,我們采用的是維特比譯碼。
最大似然譯碼:
如果所有碼字都是等概率發送,則最佳的譯碼方法是:收到序列r后,譯碼器對所有個碼字計算條件概率。若某一個似然函數取最大值,則譯碼器認為碼字就是最可能發送的碼字這種譯碼方案稱為最大似然譯碼,它的譯碼錯誤概率最小,但復雜性卻隨碼長呈指數增長。
在維特比譯碼中,硬判決時,信道可假設為較理想的二進制對稱BSC信道,此時最大似然準則又可等效于最小漢明距離準則;而軟判決則常用最大似然準則。
在本題中,我們采用的是硬判決。
(2)譯碼算法:
它主要由路徑度量的“加比選”運算、度量的更新、路徑的更新、最大似然路徑的回溯等幾個過程組成。它不是在網格圖上依次比較所有的路徑,而是接收一段,計算比較一段,保留最有可能的路徑,從而使整個碼序列是一個最大似然序列。Viterbi譯碼算法的步驟可以簡述如下:
從某一時間單位j=m開始,對進入每一狀態的所有長為j段分支的部分路徑,計算部分路徑度量。對每一狀態,挑選并存貯一條有最大度量的部分路徑及其部分度量值,稱此部分路徑為幸存路徑。
j增加1,把此時刻進入每一狀態的所有分支度量,和同這些分支相連的前一時刻的幸存路徑的度量相加,得到了此時刻進入每一狀態的幸存路徑,加以存儲并刪去其它所有路徑,因此幸存路徑延長了一個分支。
若j<L+m,則重復以上各步,否則停止,譯碼器得到了有最大路徑度量的路徑。
卷積碼的距離特性決定了它的糾錯性能,而卷積碼的性能取決于所采用的譯碼方法及碼的距離特性。
調制
調制模塊基本要求:QPSK
在數字信號的調制方式,QPSK四相移鍵控是目前最常用的一種衛星數字信號調制方式,它具有較高的頻譜利用率、較強的抗干擾性、在電路上實現也較為簡單。
QPSK信號的正弦載波有4個可能的離散相位狀態,每個載波相位攜帶2個二進制信號。QPSK利用載波的四種不同相位來表征數字信息。因此,對于輸入的二進制數字序列應該進行分組,將每兩個比特編為一組;然后用四種不同的載波相位去表征它們。例如,若輸入二進制數字信息序列為10110100,則可將它們分成10,11,01,00,然后用四種不同的相位來分別表示它們。
QPSK是在M=4時的調相技術,它規定了四種載波相位,分別為45°,135°,225°,315°,
調制器
輸入的數據是二進制數字序列,為了能和四進制的載波
相位
配合起來,則需要把二進制數據變換為四進制數據,這就是說需要把二進制數字序列中每兩個比特分成一組,共有四種組合,即00,01,10,11,其中每一組稱為雙比特碼元。每一個雙比特碼元是由兩位二進制信息比特組成,它們分別代表四進制四個符號中的一個符號。QPSK中每次調制可傳輸2個信息比特,這些信息比特是通過
載波
的四種相位來傳遞的。解調器根據星座圖及接收到的載波信號的相位來判斷發送端發送的信息比特。
下圖為QPSK系統調制圖。
AWGN信道
加性高斯白噪聲AWGN(AdditiveWhiteGaussianNoise)是最基本的噪聲與干擾模型。
加性噪聲:疊加在信號上的一種噪聲,通常記為n(t),而且無論有無信號,噪聲n(t)都是始終存在的。因此通常稱它為加性噪聲或者加性干擾。
白噪聲:噪聲的功率譜密度在所有的頻率上均為一常數,則稱這樣的噪聲為白噪聲。如果白噪聲取值的概率分布服從高斯分布,則稱這樣的噪聲為高斯白噪聲。
Matlab實現:randn()
MIMO原理
在基本原理中已經介紹過
主要參數
程序塊設計
結構性和關鍵語句
信源產生
因為由randsrc()產生的信源序列是+1和-1的序列,而進行卷積碼編碼時輸入編碼器的序列必須是單極性不歸零序列,所以要將序列中的-1修改為0.
信道編碼
根據圖可得,有6個寄存器,1個輸入和2個輸出。
將編碼器的3個沖激響應寫成二進制序列,最后轉化成八進制,最后得到的結果為133,171,165,為八進制的表示形式。
其中卷積碼的解碼深度設為8
調制
在進行編寫的過程中,最初沒有想到調用Matlab已經封裝好了的QPSK的調制函數而是自己編寫了一個函數,先進行了仿真。
先進行了符號映射。
加入噪聲,因為輸入的是復信息,所以加入的噪聲為復噪聲
誤碼率和誤比特率的公式
MIMO信道模型仿真
AWGN信道
因為采用QPSK調制產生的信號是復信號,所以在信號上疊加的高斯白噪聲也應該是復噪聲。
在實際中,是將從信源來的二進制信息比特,每2比特分為一組(此例中是x1和x2),對連續的兩組比特進行星座映射,得到兩個調制符號x1,x2。把這兩個符號送入編碼器,并按照如下方式編碼
在這里,我并沒有采用將從信源傳來的信息進行分組的方式,而是假設x1和x2這兩路信息都是相同的,即均是QPSK_SO。這樣,相當于簡化了兩發兩收的模型。
這樣,在最大似然估計的條件下,得到的接收信號可以表示為
瑞利信道
在實現對瑞利信道的仿真時,因為這時候對原理有了更深刻的了解。所以就放棄了上述的假設,而是將經過Qpsk調制的消息序列進行了分組。實現了發送兩列不同的信號x1和x2的要求
兩根接收天線上接收到的信號為
根據最大似然譯碼準則
則其譯碼可以表示為如下
最后的接收輸入是與QPSK星座圖上的四個星座點進行比較的,判決的過程就是判決離哪個星座點更近。
進行QPSK解調的時候,解調輸入為output。
狀態檢驗和性能測試
信源產生
截取了隨機產生的+1,-1序列的一部分,根據代碼,將其中的-1全部替換成了0
(由于信源是隨機產生的,在不同時刻運行程序得到的序列不同)
信道編碼
結果符合題目中給出的卷積碼編碼器的形式
通過卷積信道編碼,輸入5000個信源序列,最后輸出為15000個輸出
調制
由圖可見QPSK仿真誤碼率曲線和理論誤碼率曲線重合在一起,QPSK仿真誤比特率曲線和理論誤比特率曲線也重合在一起,誤碼率約是誤比特率的兩倍,說明實驗方法是正確可行的。
QPSK信號的誤碼率:
QPSK信號的誤比特率:
最終在實現MIMO模型的時候,采用的是matlab自身封裝好的函數
結果如下所示
對應的調制方式如下圖所示。但是在《通信原理》的學習中,我們知道該QPSK調制方式錯到相鄰符號的概率較高。
MIMO信道模型仿真
AWGN信道
左邊為加上高斯白噪聲的信號,右邊為天線上接收到的信號
瑞利信道
左圖為兩根天線上接收到的信號。
上圖為判決的結果,可以看出判決的結果證是四個星座點對應的坐標
不同仿真條件下測試誤碼性能
仿真結果與分析
由上圖可以看出,隨著信噪比的增大,誤碼率逐漸降低。
假定每一根發射天線到接收天線的衰落是獨立的,并且接收及完全知道信道系數。從上述誤碼率性能曲線仿真結果可以看出,隨著接收天線數的增加,BER性能得到了很好的改善。采用信道編碼的方式也能夠改善BER性能。相對于瑞利信道,加性高斯白噪聲信道的BER較小。且隨著接收天線數的增加,空時編碼的分集增益就越高,從而性能越好。
重點研究的問題
信源產生
根據老師的要求,用randsrc函數產生信源,但是randsrc函數產生的信源是等概分布的+1和-1序列,而卷積編碼器的輸入應該是01序列,所以在進入編碼器之前應該將其中的-1變成0,引入了一個for循環。在查閱資料后發現,其實直接設定randsrc(1,N)>.5就可以直接生成01序列。
QPSK調制
在進行仿真時,最初并不知道Matlab自帶的QPSK調制的函數,所以在QPSK調制和解調的時候也花費了很多的時間。
在自己編寫的過程中,我采用的如下圖所示的星座圖
這樣的情況下,錯到相鄰符號的概率比較小,但是在實際調用程序的時候發現,實際上是采用星座點在坐標軸上的調制方法。
MIMO信道模型仿真
因為是多天線發多天線收系統,所以要知道h信道矩陣的形式。對于不同的信道,h的形式是不相同的。在實現加性高斯白噪聲信道是,認為h的值均為1,而對于瑞利信道,認為信道矩陣是隨機產生的參數值。
由于考慮到噪聲的影響,所以發送信號在通過信道之后,要疊加上噪聲。因為通過QPSK調制后的信號時復信號,所以添加的噪聲也為復噪聲。
輸出統計
Eb/N0:Eb指的是平均比特能量。
Es/N0:Es指的是平均符號能量
N0是指加性噪聲的單邊功率譜密度
對于誤比特率的計算,可以直接調用matlab的自帶函數biterr。
結論(心得體會)
通過兩個星期的課程設計,我初步了解了基于MATLAB的MIMO通信系統仿真。兩個星期的課程設計過得很快。對于MIMO通信系統,最初我們只是在《移動通信》課上有所了解,但對于它的整個實現流程實際上是陌生的。在課設開始初期,我也面臨無從下手的困境,毫無頭緒。后來我根據老師給出的基本流程圖,一步步拆解,從最初產生信源,到最終完成兩發兩收,在這個過程中,我對基于MATLAB的MIMO通信系統仿真有了比較深刻的認識。
MIMO的優點是能夠增加無線范圍并提高性能。MIMO允許多個天線同時發送和接收多個空間流。它允許天線同時傳送和接收。利用MIMO技術可以提高信道的容量,同時也可以提高信道的可靠性,降低誤碼率。前者是利用MIMO信道提供的空間復用增益,后者是利用MIMO信道提供的空間分集增益。但是,后來深入了解了我才知道,MIMO不能夠克服頻率選擇性深衰落。所以出現了OFDM和MIMO結合在一起的技術。
整個課程設計實際上是貫穿了我們所學的專業知識。其中用到了卷積碼的編碼與譯碼,是《信息處理與編碼》的知識,對于QPSK的調制,則是《通信原理》的知識,而整個兩發兩收模型的實現,更是用到了上述專業課的思想和方法,可見,要實現一個簡單的通信系統都需要這么多門課程的交叉,更不用說進行更進一步的科學研究了。
目前,4G技術已經逐漸普及,未來是必要出現更先進的通信技術,但是無論科技如何發展,后來的技術都是對先前技術的改進和突破。只有學好現有的技術,才能夠發現其中的缺陷和弊端,才能夠找準改進的方向。
通過此次課程設計,我對數字通信系統有了更進一步的認識,對Matlab強大的仿真能力有了深刻的體會。只有靜下心來,潛心研究,認真做事,才能達到最后的目標。
參考文獻
[1]周炯磐,龐沁華,續大我,吳偉陵,楊鴻文,《通信原理》,北京郵電大學出版社
[2]林云,何豐,《MIMO技術原理及應用》,人民郵電出版社
[3]3GPPTS36.212V9.2.0(2010-06)
[4]
/p-150110752.html
[5]ClaudeOestges,BrunoClerckx,《MIMO無線通信》,機械工業出版社
附錄資料:不需要的可以自行刪除
C語言圖形模式速成
第一節
圖形模式的初始化
TurboC提供了非常豐富的圖形函數,所有圖形函數的原型均在graphics.h中,本節主要介紹圖形模式的初始化、獨立圖形程序的建立、基本圖形功能、圖形窗口以及圖形模式下的文本輸出等函數。
另外,使用圖形函數時要確保有顯示器圖形驅動程序*.BGI,同時將集成開發環境options/Linker中的Graphicslib選為on,只有這樣才能保證正確使用圖形函數。
不同的顯示器適配器有不同的圖形分辨率。即是同一顯示器適配器,在不同模式下也有不同分辨率。因此,在屏幕作圖之前,必須根據顯示器適配器種類將顯示器設置成為某種圖形模式,在未設置圖形模式之前,微機系統默認屏幕為文本模式(80列,25行字符模式),此時所有圖形函數均不能工作。設置屏幕為圖形模式,可用下列圖形初始化函數:
voidfarinitgraph(intfar*gdriver,intfar*gmode,char*path);
其中gdriver和gmode分別表示圖形驅動器和模式,path是指圖形驅動程序所在的目錄路徑。有關圖形驅動器、圖形模式的符號常數及對應的分辨率見graphics.h。
圖形驅動程序由TurboC出版商提供,文件擴展名為.BGI。根據不同的圖形適配器有不同的圖形驅動程序。例如對于EGA、VGA圖形適配器就調用驅動程序EGAVGA.BGI。
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver,gmode;
gdriver=VGA;
gmode=VGAHI;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
bar3d(100,100,300,250,50,1);/*畫一長方體*/
getch();
closegraph();
return0;
}
有時編程者并不知道所用的圖形顯示器適配器種類,或者需要將編寫的程序用于不同圖形驅動器,TurboC提供了一個自動檢測顯示器硬件的函數,其調用格式為:
voidfardetectgraph(int*gdriver,*gmode);
其中gdriver和gmode的意義與上面相同。
自動進行硬件測試后進行圖形初始化:
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver,gmode;
detectgraph(&gdriver,&gmode);/*自動測試硬件*/
printf("thegraphicsdriveris%d,modeis%d\n",gdriver,gmode);/*輸出測試結果*/
getch();
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
/*根據測試結果初始化圖形*/
bar3d(100,100,300,250,50,1);/*畫一長方體*/
getch();
closegraph();
return0;
}
上例程序中先對圖形顯示器自動檢測,然后再用圖形初始化函數進行初始化設置,但TurboC提供了一種更簡單的方法,即用gdriver=DETECT語句后再跟initgraph()函數就行了。
采用這種方法后,上例可改為:
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver=DETECT,gmode;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
bar3d(50,50,150,30,50,1);
getch();
closegraph();
return0;
}
另外,TurboC提供了退出圖形狀態的函數closegraph(),其調用格式為:
voidfarclosegraph(void);
第二節
屏幕顏色的設置和清屏函數
對于圖形模式的屏幕顏色設置,同樣分為背景色的設置和前景色的設置。在TurboC中分別用下面兩個函數:
設置背景色:
voidfarsetbkcolor(intcolor);
設置作圖色:
voidfarsetcolor(intcolor);
其中color為圖形方式下顏色的規定數值,對EGA,VGA顯示器適配器,有關顏色的符號常數及數值見graphics.h。
清除圖形屏幕內容但不清除圖形背景使用清屏函數,其調用格式如下:
voidefarcleardevice(void);
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver,gmode,i,aa;
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");/*圖形初始化*/
setbkcolor(0);/*設置圖形背景*/
cleardevice();
for(i=0;i<=15;i++)
{
setcolor(i);/*設置不同作圖色*/
circle(320,240,20+i*10);/*畫半徑不同的圓*/
getch();
}
for(i=0;i<=15;i++)
{
setbkcolor(i);/*設置不同背景色*/
cleardevice();
circle(320,240,20+i*10);
getch();
}
aa=getmaxcolor();
printf("maxcolor=%d",aa);
getch();
closegraph();
return0;
}
另外,TURBOC也提供了幾個獲得現行顏色設置情況的函數。
intfargetbkcolor(void);
返回現行背景顏色值。
intfargetcolor(void);
返回現行作圖顏色值。
intfargetmaxcolor(void);
返回最高可用的顏色值。
第三節
基本畫圖函數
基本圖形函數包括畫點,線以及其它一些基本圖形的函數。本節對這些函數作一全面的介紹。
1、畫點
I.畫點函數
voidfarputpixel(intx,inty,intcolor);
該函數表示有指定的象元畫一個按color所確定顏色的點。對于顏色color的值可從表3中獲得而對x,y是指圖形象元的坐標。
在圖形模式下,是按象元來定義坐標的。對VGA適配器,它的最高分辨率為640x480,其中640為整個屏幕從左到右所有象元的個數,480為整個屏幕從上到下所有象元的個數。屏幕的左上角坐標為(0,0),右下角坐標為(639,479),水平方向從左到右為x軸正向,垂直方向從上到下為y軸正向。TURBOC的圖形函數都是相對于圖形屏幕坐標,即象元來說的。
關于點的另外一個函數是:
intfargetpixel(intx,inty);
它獲得當前點(x,y)的顏色值。
II、有關坐標位置的函數
intfargetmaxx(void);
返回x軸的最大值。
intfargetmaxy(void);
返回y軸的最大值。
intfargetx(void);
返回游標在x軸的位置。
voidfargety(void);
返回游標有y軸的位置。
voidfarmoveto(intx,inty);
移動游標到(x,y)點,不是畫點,在移動過程中亦畫點。
voidfarmoverel(intdx,intdy);
移動游標從現行位置(x,y)移動到(x+dx,y+dy)的位置,移動過程中不畫點。
2、畫線
I.畫線函數
TURBOC提供了一系列畫線函數:
voidfarline(intx0,inty0,intx1,inty1);
畫一條從點(x0,y0)到(x1,y1)的直線。
voidfarlineto(intx,inty);
畫一作從現行游標到點(x,y)的直線。
voidfarlinerel(intdx,intdy);
畫一條從現行游標(x,y)到按相對增量確定的點(x+dx,y+dy)的直線。
voidfarcircle(intx,inty,intradius);
以(x,y)為圓心,radius為半徑,畫一個圓。
voidfararc(intx,inty,intstangle,intendangle,intradius);
以(x,y)為圓心,radius為半徑,從stangle開始到endangle結束(用度表示)畫一段圓弧線。
在TURBOC中規定x軸正向為0度,逆時針方向旋轉一周,依次為90,180,270和360度(其它有關函數也按此規定,不再重述)。
voidellipse(intx,inty,intstangle,intendangle,intxradius,intyradius);
以(x,y)為中心,xradius,yradius為x軸和y軸半徑,從角stangle開始到endangle結束畫一段橢圓線,當stangle=0,endangle=360時,畫出一個完整的橢圓。
voidfarrectangle(intx1,inty1,intx2,inty2);
以(x1,y1)為左上角,(x2,y2)為右下角畫一個矩形框。
voidfardrawpoly(intnumpoints,intfar*polypoints);
畫一個頂點數為numpoints,各頂點坐標由polypoints給出的多邊形。polypoints整型數組必須至少有2倍頂點數個無素。每一個頂點的坐標都定義為x,y,并且x在前。值得注意的是當畫一個封閉的多邊形時,numpoints的值取實際多邊形的頂點數加一,并且數組polypoints中第一個和最后一個點的坐標相同。
下面舉一個用drawpoly()函數畫箭頭的例子。
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver,gmode,i;
intarw[16]={200,102,300,102,300,107,330,
100,300,93,300,98,200,98,200,102};
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbkcolor(BLUE);
cleardevice();
setcolor(12);/*設置作圖顏色*/
drawpoly(8,arw);/*畫一箭頭*/
getch();
closegraph();
return0;
}
II、設定線型函數
在沒有對線的特性進行設定之前,TURBOC用其默認值,即一點寬的實線,但TURBOC也提供了可以改變線型的函數。
線型包括:寬度和形狀。其中寬度只有兩種選擇:一點寬和三點寬。而線的形狀則有五種。
下面介紹有關線型的設置函數。
voidfarsetlinestyle(intlinestyle,unsignedupattern,intthickness);
該函數用來設置線的有關信息,其中linestyle是線形狀的規定,見graphics.h。
對于upattern,只有linestyle選USERBIT_LINE時才有意義(選其它線型,uppattern取0即可)。此時uppattern的16位二進制數的每一位代表一個象元,如果那位為1,則該象元打開,否則該象元關閉。
voidfargetlinesettings(structlinesettingstypefar*lineinfo);
該函數將有關線的信息存放到由lineinfo指向的結構中,表中linesettingstype的結構如下:
structlinesettingstype{
intlinestyle;
unsignedupattern;
intthickness;
}
例如下面兩句程序可以讀出當前線的特性
structlinesettingstype*info;
getlinesettings(info);
voidfarsetwritemode(intmode);
該函數規定畫線的方式。如果mode=0,則表示畫線時將所畫位置的原來信息覆蓋了(這是TURBOC的默認方式)。如果mode=1,則表示畫線時用現在特性的線與所畫之處原有的線進行異或(XOR)操作,實際上畫出的線是原有線與現在規定的線進行異或后的結果。因此,當線的特性不變,進行兩次畫線操作相當于沒有畫線。
有關線型設定和畫線函數的例子如下所示。
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver,gmode,i;
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbkcolor(BLUE);
cleardevice();
setcolor(GREEN);
circle(320,240,98);
setlinestyle(0,0,3);/*設置三點寬實線*/
setcolor(2);
rectangle(220,140,420,340);
setcolor(WHITE);
setlinestyle(4,0xaaaa,1);/*設置一點寬用戶定義線*/
line(220,240,420,240);
line(320,140,320,340);
getch();
closegraph();
return0;
}
第四節
基本圖形的填充
填充就是用規定的顏色和圖模填滿一個封閉圖形。一般是先畫輪廓再填充。
TURBOC提供了一些先畫出基本圖形輪廓,再按規定圖模和顏色填充整個封閉圖形的函數。在沒有改變填充方式時,TURBOC以默認方式填充。
voidfarbar(intx1,inty1,intx2,inty2);
確定一個以(x1,y1)為左上角,(x2,y2)為右下角的矩形窗口,再按規定圖模和顏色填充。說明:此函數不畫出邊框,所以填充色為邊框。
voidfarbar3d(intx1,inty1,intx2,inty2,intdepth,inttopflag);
當topflag為非0時,畫出一個三維的長方體。當topflag為0時,三維圖形不封頂,實際上很少這樣使用。說明:bar3d()函數中,長方體第三維的方向不隨任何參數而變,即始終為45度的方向。
voidfarpieslice(intx,inty,intstangle,intendangle,intradius);
畫一個以(x,y)為圓心,radius為半徑,stangle為起始角度,endangle為終止角度的扇形,再按規定方式填充。當stangle=0,endangle=360時變成一個實心圓,并在圓內從圓點沿X軸正向畫一條半徑。
voidfarsector(intx,inty,intstanle,intendangle,intxradius,intyradius);
畫一個以(x,y)為圓心分別以xradius,yradius為x軸和y軸半徑,stangle為起始角,endangle為終止角的橢圓扇形,再按規定方式填充。
第五節
設定填充方式
TURBOC有四個與填充方式有關的函數。下面分別介紹:
voidfarsetfillstyle(intpattern,intcolor);
color的值是當前屏幕圖形模式時顏色的有效值。pattern的值及與其等價的符號常數見graphics.h。
除USER_FILL(用戶定義填充式樣)以外,其它填充式樣均可由setfillstyle()函數設置。當選用USER_FILL時,該函數對填充圖模和顏色不作任何改變。之所以定義USER_FILL主要因為在獲得有關填充信息時用到此項。
voidfarsetfillpattern(char*upattern,intcolor);
設置用戶定義的填充圖模的顏色以供對封閉圖形填充。其中upattern是一個指向8個字節的指針。這8個字節定義了8x8點陣的圖形。每個字節的8位二進制數表示水平8點,8個字節表示8行,然后以此為模型向個封閉區域填充。
voidfargetfillpattern(char*upattern);
該函數將用戶定義的填充圖模存入upattern指針指向的內存區域。
voidfargetfillsetings(structfillsettingstypefar*fillinfo);
獲得現行圖模的顏色并將存入結構指針變量fillinfo中。其中fillsettingstype結構定義如下:
structfillsettingstype{
intpattern;/*現行填充模式*/
intcolor;/*現行填充模式*/
};
有關圖形填充圖模的顏色的選擇,請看下面例程。
#include"stdio.h"
#include"graphics.h"
main()
{
charstr[8]={10,20,30,40,50,60,70,80};/*用戶定義圖模*/
intgdriver,gmode,i;
structfillsettingstypesave;
/*定義一個用來存儲填充信息的結構變量*/
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbkcolor(BLUE);
cleardevice();
for(i=0;i<13;i++)
{
setcolor(i+3);
setfillstyle(i,2+i);/*設置填充類型*/
bar(100,150,200,50);/*畫矩形并填充*/
bar3d(300,100,500,200,70,1);/*畫長方體并填充*/
pieslice(200,300,90,180,90);/*畫扇形并填充*/
sector(500,300,180,270,200,100);/*畫橢圓扇形并填充*/
getch();
}
cleardevice();
setcolor(14);
setfillpattern(str,RED);
bar(100,150,200,50);
bar3d(300,100,500,200,70,0);
pieslice(200,300,0,360,90);
sector(500,300,0,360,100,50);
getch();
getfillsettings(&save);
/*獲得用戶定義的填充模式信息*/
closegraph();
clrscr();
printf("Thepatternis%d,Thecoloroffillingis%d",
save.pattern,save.color);
/*輸出目前填充圖模和顏色值*/
getch();
}
第六節
任意封閉圖形的填充
截止目前為止,我們只能對一些特定形狀的封閉圖形進行填充,但還不能對任意封閉圖形進行填充。為此,TURBOC提供了一個可對任意封閉圖形填充的函數,其調用格式如下:
voidfarfloodfill(intx,inty,intborder);
其中:x,y為封閉圖形內的任意一點,border為邊界的顏色,也就是封閉圖形輪廓的顏色。調用了該函數后,將用由函數setfillstyle()規定的顏色和模式填滿整個封閉圖形。
注意:
a.如果x或y取在邊界上,則不進行填充。
b.如果不是封閉圖形則填充會從沒有封閉的地方溢出去,填滿其它地方。
c.如果x或y在圖形外面,則填充封閉圖形外的屏幕區域。
d.由border指定的顏色值必須與圖形輪廓的顏色值相同,但填充色可選任意顏色。
下例是有關floodfill()函數的用法,該程序填充了bar3d()所畫長方體中其它兩個未填充的面。
#include"stdio.h"
#include"graphics.h"
main()
{
intgdriver,gmode;
structfillsettingstypesave;
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbkcolor(BLUE);
cleardevice();
setcolor(LIGHTRED);
setlinestyle(0,0,3);
setfillstyle(1,14);/*設置填充方式*/
bar3d(100,200,400,350,200,1);/*畫長方體并填充*/
floodfill(450,300,LIGHTRED);
/*填充長方體另外兩個面*/
floodfill(250,150,LIGHTRED);
rectangle(450,400,500,450);/*畫一矩形*/
floodfill(470,420,LIGHTRED);/*填充矩形*/
getch();
closegraph();
}
第七節屏幕操作函數
除了清屏函數以外,關于屏幕操作還有以下函數:
voidfarsetactivepage(intpagenum);
voidfarsetvisualpage(intpagenum);
這兩個函數只用于EGA,VGA以及HERCULES圖形適配器。setctivepage()函數是為圖形輸出選擇激活頁。
所謂激活頁是指后續圖形的輸出被寫到函數選定的pagenum頁面,該頁面并不一定可見。setvisualpage()函數才使pagenum所指定的頁面變成可見頁。頁面從0開始(TurboC默認頁)。如果先用setactivepage()函數在不同頁面上畫出一幅幅圖像,再用setvisualpage()函數交替顯示,就可以實現一些動畫的效果。
voidfargetimage(intxl,intyl,intx2,inty2,voidfar*mapbuf);
voidfarputimge(intx,int,y,void*mapbuf,intop);
unsinedfarimagesize(intxl,intyl,intx2,inty2);
這三個函數用于將屏幕上的圖像復制到內存,然后再將內存中的圖像送回到屏幕上。首先通過函數imagesize()測試要保存左上角為(xl,yl),右上角為(x2,y2)的圖形屏幕區域內的全部內容需多少個字節,然后再給mapbuf分配一個所測數字節內存空間的指針。通過調用getimage()函數就可將該區域內的圖像保存在內存中,需要時可用putimage()函數將該圖像輸出到左上角為點(x,y)的位置上,其中getimage()函數中的參數op規定如何釋放內存中圖像。關于這個參數的定義參見下表。
對于imagesize()函數,只能返回字節數小于64K字節的圖像區域,否則將會出錯,出錯時返回-1。本節介紹的函數在圖像動畫處理、菜單設計技巧中非常有用。
下面程序模擬兩個小球動態碰撞過程。
#include"stdio.h"
#include"graphics.h"
#include"malloc.h"
intmain()
{
inti,gdriver,gmode,size;
void*buf;
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbkcolor(BLUE);
cleardevice();
setcolor(LIGHTRED);
setlinestyle(0,0,1);
setfillstyle(1,10);
circle(100,200,30);
floodfill(100,200,12);
size=imagesize(69,169,131,231);
buf=malloc(size);
if(!buf)return-1;
getimage(69,169,131,231,buf);
putimage(500,269,buf,COPY_PUT);
for(i=0;i<185;i++){
putimage(70+i,170,buf,COPY_PUT);
putimage(500-i,170,buf,COPY_PUT);
}
for(i=0;i<185;i++){
putimage(255-i,170,buf,COPY_PUT);
putimage(315+i,170,buf,COPY_PUT);
}
getch();
closegraph();
}
第八節用戶對文本字符大小的設置
前面介紹的settextstyle()函數,可以設定圖形方式下輸出文本字符這字體和大小但對于筆劃型字體(除8*8點陣字以個的字體),只能在水平和垂直方向以相同的放大倍數放大。
為此TurboC2.0又提供了另外一個setusercharsize()函數,對筆劃字體可以分別設置水平和垂直方向的放大倍數。該函數的調用格式為:
voidfarsetusercharsize(intmulx,intdivx,intmuly,intdivy);
該函數用來設置筆劃型字和放大系數,它只有在settextstyle()函數中的charsize為0(或USER_CHAR_SIZE)時才起作用,并且字體為函數settextstyle()規定的字體。
調用函數setusercharsize()后,每個顯示在屏幕上的字符都以其缺省大小乘以mulx/divx為輸出字符寬,乘以muly/divy為輸出字符高。
#include"stdio.h"
#include"graphics.h"
intmain()
{
intgdriver,gmode;
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbkcolor(BLUE);
cleardevice();
setfillstyle(1,2);/*設置填充方式*/
setcolor(WHITE);/*設置白色作圖*/
rectangle(100,100,330,380);
floodfill(50,50,14);/*填充方框以外的區域*/
setcolor(12);/*作圖色為淡紅*/
settextstyle(1,0,8);/*三重筆劃字體,放大8倍*/
outtextxy(120,120,"VeryGood");
setusercharsize(2,1,4,1);
/*水平放大2倍,垂直放大4倍*/
setcolor(15);
settextstyle(3,0,5);
/*無襯字筆劃,放大5倍*/
outtextxy(220,220,"VeryGood");
setusercharsize(4,1,1,1);
settextstyle(3,0,0);
outtextxy(180,320,"Good");
getch();
closegraph();
return0;
}
第九節文本字體、字型和輸出方式的設置
有關圖形方式下的文本輸出函數,可以通過setcolor()函數設置輸出文本的顏色。另外,也可以改變文本字體大小以及選擇是水平方向輸出還是垂直方向輸出。
voidfarsettexjustify(inthoriz,intvert);
該函數用于定位輸出字符串。對使用outtextxy(intx,inty,charfar*strtextstring)函數所輸出的字符串,其中哪個點對應于定位坐標(x,y)在TurboC2.0中是有規定的。如果把一個字符串看成一個長方形的圖形,在水平方向顯示時,字符串長方形按垂直方向可分為頂部,中部和底部三個位置,水平方向可分為左,中,右三個位置,兩者結合就有9個位置。settextjustify()函數的第一個參數horiz指出水平方向三個位置中的一個,第二個參數vert指出垂直方向三個位置中的一個,二者就確定了其中一個位置。當規定了這個位置后,用outtextxy()函數輸出字符串時,字符串長方形的這個規定位置就對準函數中的(x,y)位置。而對用uttext()函數輸出字符串時,這個規定的位置就位于現行游標的位置。
有關參數horiz和vert的取值參見graphics.h。
voidfarsettextstyle(intfont,intdirection,intcharsize);
該函數用來設置輸出字符的字形(由font確定)、輸出方向(由direction確定)和字符大小(由charsize確定)等特性。
TurboC2.0對函數中各個參數的規定見graphics.h。
有關圖形屏幕下文本輸出和字體字型設置函數的用法請看下例:
#include"stdio.h"
#include"graphics.h"
intmain()
{
inti,gdriver,gmode;
chars[30];
gdriver=DETECT;
initgraph(&gdriver,&gmode,"C:\\TC2.0\\BGI");
setbk
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經權益所有人同意不得將文件中的內容挪作商業或盈利用途。
- 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
- 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 中職班主任能力大賽培訓
- 中班健康會傳染的紅眼病教案
- 《愛的教育》閱讀指導課
- 腫瘤科常見藥物及不良反應
- 癌痛持續加重患者的護理
- 各人藥品知識培訓心得體會
- 中國基礎教育政策發展路徑
- 美甲培訓費用分析
- 左乳癌患者的護理
- 文化創意產業廠房施工安全與環保合同書
- 2025屆湖南長沙雅禮實驗中學七年級數學第二學期期末學業水平測試試題含解析
- 天津市濱海新區第四共同體2025年八下物理期末復習檢測試題含解析
- 客服投訴處理技巧培訓
- 醫學檢驗倫理規范與實踐
- TCWEA6-2019水利水電工程施工期度汛方案編制導則
- 《微信公眾號如何申請》課件
- 廣東省廣州市越秀區2024-2025學年八年級下學期期中考試數學檢測試卷(含答案)
- 2024年CAD工程師認證考試的題型解析試題及答案
- 2025年北方華創工作人員招聘考試筆試試題
- 2025-2030中國救護車市場發展分析及市場趨勢與投資方向研究報告
- 2025成都勞動合同范本
評論
0/150
提交評論