PBRT學習筆記: 顏色在離線渲染中的表示方法

本文簡單總結下PBRT中的第五章的前半部分,是關於光譜的一些內容。這部分的內容相對而言比較獨立,不受其他模塊的制約。
計算機是一個有限的資源,我們的顯示器同樣是只能表示有限的信息量。舉個簡單的例子,對於一個普通的LCD 22寸的顯示器而言,假設分辨率是1650*1080,而每個pixel只能表現出2的24次冪種不同的顏色,那麼實際上一個屏幕最多能表示的信息也就是1650*1080*(2^24)。這裏我們拋開分辨率不談,只考慮一個pixel所能表示的信息量,其實只有2^24種不同顏色的表現能力。而我們現實生活中的顏色範圍是非常廣泛的,要遠遠大於這個數值,所以我們需要一種映射方式把現實生活中的光譜信息抽象到顯示器所能表示的形式。從某種角度理解,我們可以理解爲這是一種把一個接近無限的集合映射到一個有限集合的過程。顯然這肯定不是一一映射了,前者中的任何一個數據只能對應後者中的相對應的唯一的一個數據,而反過來則未必。
首先,我們先簡單解釋下計算機中對於顏色的表示方法。這裏就介紹兩種比較常用的好了。第一種是我們最熟悉的RGB表示方法,即紅綠藍表示法。任何一個pixel所能表示的顏色由紅綠藍三原色組成,每個單獨的通道一般用一個byte表示。另一種表示方法相對用的較少,每個顏色XYZ三種分量來控制。相對來說,這個比較難理解一些。不過就本質來講,兩者的差別不大,只是兩種表示形式而已,是可以互相轉換的。
在簡單瞭解了計算機內部的顏色表示後,我們來了解下生活中的顏色的表示方法吧。中學的時候,大家都學過光具有波粒二項性。這裏面我們只談光波的性質吧,每個單獨的光線都是有波長的,不同的波長在人眼中的表現形式是不一樣的。波長在400左右的光在我們眼中表現爲藍光,波長爲550的光表現爲綠光,而波長在650左右的光波則表現爲紅光。在這個範圍之外的,我們認爲是紅外線和紫外線,對於渲染而言,是沒啥意義的,所以基本不用考慮。而我們在生活中看到的光線基本上都是很多光束混合到一起的,所以其波長並不一致,從而導致了我們可以看到多種多樣的不同的顏色。所以我們可以用光譜來表示我們看到的光的信息。我對光譜的理解很淺,光譜大概是把光束按照光的波長分開,然後把每個波長的光強度記錄下來,從而形成一條曲線,這條曲線可以被用來表示光的信息。
image上圖中分別爲熒光燈和檸檬的光譜圖(這樣說可能不太標準)。對於前者而言,我們注意到其能量是很大的,但是曲線相對較陡,所以我們看到的熒光燈會很亮,而且顏色鮮明。而後者的光譜中的曲線就很緩,而且能量也小很多。
那麼對於離線渲染,如果想支持光譜的表示的話,必須把上面的光譜圖離散化。其實PBRT的做法並不複雜,它把光按照波長從400到700平均分成k等分,在每個k等分點取光譜的能量值。當k的值足夠大的時候,這條曲線基本可以被表示出來。而對於光譜的數據源,一般是來源於文件的。這些文件中的數據都是經過前人實驗總結出來的。
現在我們瞭解了計算機中的顏色表示方法和光譜的離散表示方法,那麼兩者之間的聯繫是什麼樣呢?即使在進行離線渲染過程中,我們都用光譜來表示顏色,最後我們依然要把顏色轉換爲RGB的形式,從而確保顯示器可以正確顯示,因爲畢竟顯示器是不知道如何解析光譜信息的。
這裏我們先考慮XYZ與光譜信息之間的關係吧,我們用X、Y、Z來表示三個分量。人眼的主要特性決定了其對於顏色的感知可以由三個浮點數字有效的表示。首先需要定義/overline{x}(/lambda) , /overline{y}(/lambda)/overline{z}(/lambda) 。他們被稱爲color-matching functions。其實是三個光譜分佈,大致的形狀如下:
File:CIE 1931 XYZ Color Matching Functions.svg注意這裏的三條曲線絕對不代表是RGB的三條曲線,只不過是有些近似而已。那麼對於任意的一個光譜分佈I(/lambda)/, ,我們都可以把它轉換爲X、Y、Z的表示法。
image這樣就可以把光譜信息轉換爲XYZ的表示法了。(注,上述公式是在wiki裏面查到的,與pbrt第二版的內容稍有不符。不敢輕易下定論是哪一個錯誤)
本質上來講,上述過程相當於一個降維的過程。可以這樣考慮,對於光譜分佈的任何一個曲線,由於計算機內部是離散表示的,所以實際是一個k維數組而已。那麼這個k維數組的每個實例我們可以理解爲是在k維空間中的一個點。而/overline{x}(/lambda) , /overline{y}(/lambda)/overline{z}(/lambda) 可以認爲是三個k維軸,用來把k維空間中的點映射到三維空間,即XYZ。這個過程有一點點像PCA的過程,只不過主成分不是根據點集的variation決定的,而是根據人眼的對於顏色的感知特性決定的。
貌似對於上述表示法,已經足夠高效而簡潔的表示一個顏色了。但是事實上,很多應用中,這種表示法並不合適。考慮兩個顏色實例,假設光譜爲a0,a1,分別轉換爲(x0,y0,z0)和(x1,y1,z1)。那麼a0與a1的乘積結果a2同樣轉換成了(x2,y2,z2),可是x2!=x0*x1,y2!=y0*y1,z2!=z0*z1。這對於很多操作是非常不方便的。所以人們又引入了RGB顏色空間,從而解決上述問題。
光譜信息映射到RGB顏色空間與之前的XYZ映射過程是沒有本質區別的,只是三條曲線不同而已。這裏就不列出三條曲線的形狀了。而有了上述的兩種映射關係,XYZ與RGB之間的映射關係就變味簡單的矩陣變換了。這裏就不一一列出了,想了解的朋友自己查一下相關資料吧。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章