【十天自制軟渲染器】DAY 01:圖形學(xué)學(xué)習(xí)建議與環(huán)境搭建

推薦直接閱讀博客原文,更新更及時(shí),閱讀體驗(yàn)更佳

如果你覺得我寫的不錯(cuò),就給我個(gè)點(diǎn)個(gè)贊吧??!謝謝你,這對(duì)我真的很重要!

十天自制軟渲染器」這個(gè)標(biāo)題我承認(rèn)標(biāo)題黨了.在對(duì)圖形學(xué)一無所知的情況下想十天自制一個(gè)軟渲染器,就好似一節(jié)課沒上過卻試圖一個(gè)晚上看完《30 天精通 C++》然后第二天早上八點(diǎn)考試得滿分一樣,我承認(rèn)世界上有這種天才,但很可惜我不是。

就像前文所說,本系列造的輪子都是站在巨人的肩膀上完成的,需要對(duì)相關(guān)知識(shí)有一定的了解和學(xué)習(xí),如果你是一個(gè)圖形學(xué)大牛,這種軟渲染器肯定是不屑于做的;如果你剛剛進(jìn)入圖形學(xué)的大門,造一個(gè)軟渲染器的輪子,非常利于你鞏固自己的底層知識(shí)。

<br />

本文主要(90%)參考 ssloy 大神的 tinyrenderer 教程,零依賴實(shí)現(xiàn)一個(gè)軟渲染器,通過這個(gè)教程可以實(shí)現(xiàn)一個(gè)簡(jiǎn)易版本的 OpenGL2.0(即 rendering pipeline 只支持 Vertex ShaderFragment Shader 兩種自定義 Shader 類型),了解 OpenGL 這類圖形學(xué) API 在底層是如何工作的。

我自己造的輪子是 toyRenderer,在 tinyrenderer 的基礎(chǔ)上加入了大量的注釋并按自己的理解優(yōu)化了部分代碼(不排除有反向優(yōu)化),如果大家對(duì) tinyrenderer 感興趣,可以參考一下我的實(shí)現(xiàn)和我現(xiàn)在寫的這個(gè)教程,點(diǎn)個(gè) star ?? 就更好不過了~

本專欄的目錄結(jié)構(gòu)和 tinyrenderer 保持一致,方便大家對(duì)比閱讀。

<br />

前置知識(shí)

要想看懂 tinyrenderer 的代碼,需要有一定的知識(shí)儲(chǔ)備,下面是我在造輪子時(shí)的一些總結(jié),大家學(xué)習(xí)前可以參考一下。

1.數(shù)學(xué)

對(duì)于圖形學(xué)來說,數(shù)學(xué)是一道繞不過的坎兒;對(duì)于這個(gè)軟渲染器器輪子來說,并沒有涉及太多的數(shù)學(xué)內(nèi)容,我個(gè)人總結(jié)如下:

1.1 高中數(shù)學(xué)

造一個(gè)軟渲染器需要你還記得一些高中幾何的內(nèi)容,難度都不大,比如說直線的坐標(biāo)公式,重心坐標(biāo)等。

1.2 微積分

微積分其實(shí)只有少量的涉及,原教程里有一點(diǎn)點(diǎn)梯度的內(nèi)容,個(gè)人感覺對(duì)整體學(xué)習(xí)進(jìn)度影響不大。

1.3 線性代數(shù)

線性代數(shù)涉及的內(nèi)容比較多,從最簡(jiǎn)單的向量,再到各種坐標(biāo)系變換,都需要對(duì)線性代數(shù)有比較扎實(shí)的理解。

如果你線性代數(shù)都忘的差不多了,這里我推薦 3Blue1Brown 的教程——《線性代數(shù)的本質(zhì)》,這是我見過最好的線性代數(shù)入門教程了。而且圖形學(xué)里涉及的矩陣變換絕大部分都是三維空間的,基本上看完這門課就可以上手圖形學(xué)的學(xué)習(xí)了。

3Blue1Brown——線性代數(shù)的本質(zhì)

<br />

2.圖形學(xué)

圖形學(xué)入門課程我只推薦一個(gè),閆令琪大神的《GAMES101-現(xiàn)代計(jì)算機(jī)圖形學(xué)入門》。

GAMES101-現(xiàn)代計(jì)算機(jī)圖形學(xué)入門

閆令琪大神有多厲害我就不多介紹了,最關(guān)鍵的是 GAMES101 優(yōu)點(diǎn)太多了:

  • 全中文講解,大大降低國(guó)內(nèi)小伙伴的學(xué)習(xí)門檻
  • 課程非常新,2020 年初才開課,不會(huì)存在課程/教案過時(shí)的情況
  • 知識(shí)點(diǎn)全面,正如課程名「現(xiàn)代圖形學(xué)入門」,本課程不但講了經(jīng)典的光柵化成像,還講了光線追蹤等相對(duì)較新較前沿的內(nèi)容

學(xué)完這門課可以收獲什么呢?比如說 2077 的圖形設(shè)置面板你都知道是啥意思了

2077 圖形設(shè)置面板

如果跟著這門課學(xué)下來,其實(shí)課下作業(yè)就會(huì)完成一個(gè)小的軟渲染器,但由于我是后期才加入學(xué)習(xí)的,所以作業(yè)也沒有跟著做,經(jīng)過搜索發(fā)現(xiàn) tinyrenderer 這個(gè)教程推薦的人最多,所以最后參照這個(gè)教程實(shí)現(xiàn)了自己的軟渲染器。

閆老師的是視頻教程,大家可以配合他的 PPT 學(xué)習(xí)。如果習(xí)慣看書,我這里推薦兩本,一本是大名鼎鼎的虎書《Fundamentals of Computer Graphics 4th Edition》,另一本是《Real Time Rendering 4th》,都是非常經(jīng)典非常有名的書籍。

Graphics Books

這兩本書國(guó)內(nèi)都沒有引進(jìn),我這里有英文版的 PDF,大家可以看我個(gè)人簡(jiǎn)介,關(guān)注「鹵蛋實(shí)驗(yàn)室」后回復(fù)「圖形學(xué)」獲取下載鏈接。

<br />

3.C++

本渲染器是用 C++ 寫的,但用到的都是基礎(chǔ)語法,稍微高級(jí)點(diǎn)兒的知識(shí)就是模版編程和操作符重載。個(gè)人認(rèn)為只要有其他語言基礎(chǔ),看個(gè)半小時(shí)的 C++ 語法就可以上手實(shí)踐了。

<br />

如果上面的三個(gè)知識(shí)點(diǎn)都掌握的差不多了,我打保票十天內(nèi)肯定能寫出一個(gè)軟渲染器;如果沒有掌握好(尤其是圖形學(xué)基礎(chǔ)知識(shí)),十天內(nèi)實(shí)現(xiàn)是有些夠嗆。廢話不多說,我們先去搭環(huán)境吧!


本教程要做的是一個(gè)零依賴軟渲染器,所以依賴的環(huán)境就是 C++ 的開發(fā)環(huán)境。

注:零依賴意味著這個(gè)項(xiàng)目不依賴任何第三方庫,軟渲染意味著所有計(jì)算都是在 CPU 側(cè)進(jìn)行的,沒有 GPU 參與

C++ 環(huán)境搭建配置有多種方法,最快捷的方式就是直接用高度集成的 IDE,win 電腦可以用 Visual Studio,Mac 用戶可以用 Xcode。當(dāng)然你也可以用 CMake + VSCode 搭建 C++ 運(yùn)行環(huán)境。

我這個(gè)人很懶,平常開發(fā) Xcode 用的又比較多,不想多折騰了,所以直接用 Xcode 構(gòu)建項(xiàng)目了,小伙伴們千萬不要學(xué)習(xí)我這種壞習(xí)慣。

Xcode 創(chuàng)建 C++ 項(xiàng)目

1.新建項(xiàng)目

1.Xcode 創(chuàng)建 C++ 項(xiàng)目非常簡(jiǎn)單,啟動(dòng) XCode 后點(diǎn)擊 Create a new Xcode project,創(chuàng)建一個(gè)新項(xiàng)目

image

<br />

2.在跳出的彈框里選擇 Command Line Tool,然后點(diǎn)擊 Next

image

<br />

3.在新的彈窗里填寫好 Product NameLanguage 選擇 C++,然后點(diǎn)擊 Next

image

<br />

4.在新的彈窗里選擇項(xiàng)目路徑,點(diǎn)擊 Create 創(chuàng)建項(xiàng)目

到這里項(xiàng)目就創(chuàng)建好了。

2.配置相對(duì)路徑

軟渲染器需要對(duì)硬盤上的一些文件做一些 IO 操作,這時(shí)候就需要配置項(xiàng)目的相對(duì)路徑。

首先按照 Product -> Scheme -> Edit Scheme 的次序,打開一個(gè)彈窗。

然后在彈窗里勾選 Using custom working directory,并選擇項(xiàng)目文件所在路徑就可:

image

3.把源代碼拖進(jìn)去

因?yàn)楸卷?xiàng)目是零依賴的,渲染方式是根據(jù)源代碼生成一張 tga 格式的圖片。因?yàn)槲覀兪莵韺戃涗秩酒鞫皇菍憟D片編碼器的,所以直接把源代碼里的 tgaimage.htgaimage.cpp 拖到我們的項(xiàng)目工程里就可以了。

加上 main.cpp,現(xiàn)在的工程目錄里只有三個(gè)文件

.
├── main.cpp
├── tgaimage.cpp
└── tgaimage.h

然后我們?cè)?main.cpp 里寫一些簡(jiǎn)單的代碼——?jiǎng)?chuàng)建一個(gè) 100x100 的圖片,在 (52, 41) 這個(gè)坐標(biāo)上畫一個(gè)紅的的點(diǎn)(rgb(255, 0, 0)

#include "tgaimage.h"

const TGAColor red = TGAColor(255, 0, 0, 255);

int main(int argc, char** argv) {
  TGAImage image(100, 100, TGAImage::RGB);
  image.set(52, 41, red);
  image.flip_vertically();
  image.write_tga_file("output/lesson00.tga");
  return 0;
}

點(diǎn)擊 Xcode 左上角三角形的 build 按鈕,如果編譯成功并在 output 這個(gè)文件夾下生成一張名為 lesson00.tga 的圖片,就說明環(huán)境配置成功了!
(紅點(diǎn)只有一個(gè)像素大,看不清可以點(diǎn)擊查看大圖)

image

<br />

<br />

今天在圖片上畫了一個(gè)點(diǎn),明天我們就學(xué)習(xí)一下如何高性能的畫一條直線。


如果你覺得我寫的不錯(cuò),就給我個(gè)點(diǎn)個(gè)贊吧??!謝謝你,這對(duì)我真的很重要!

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容