1. 程式人生 > >用JavaScript玩轉計算機圖形學(一)光線追蹤入門

用JavaScript玩轉計算機圖形學(一)光線追蹤入門

系列簡介

記得小時候讀過一本關於計算機圖形學(computer graphics, CG)的入門書,從此就愛上了CG。本系列希望,採用很多人認識的JavaScript語言去分享CG,令更多人有機會接觸,並愛上CG。

本系列的特點之一,是讀者能在瀏覽器裡直接執行程式碼,也可重覆修改程式碼測試。透過這種互動,也許能更深刻體會內容。讀者只要懂得JavaScript(因為JavaScript很簡單,學過Java/C/C++/C#之類的語言也應沒問題)和一點點線性代數(linear algebra)就可以了。

筆者在大學期間並沒有修讀CG課程,雖然看過相關書籍,始終未親手做過全域光照的渲染器,本文也作為個人的學習分享。此外,筆者也差不多十年沒接觸JavaScript,希望各位不吝賜教。

本文簡介

多數程式設計師聽到3D CG,就會聯想到Direct3D、OpenGL等API。事實上,這些流行的API主要為實時渲染(real-time rendering)而設,一般採用光柵化(rasterization)方式,渲染大量的三角形(或其他幾何圖元種類(primitive types))。這種基於光柵化的渲染系統,只支援區域性光照(local illumination)。換句話說,渲染幾何圖形的一個畫素時,光照計算只能取得該畫素的資訊,而不能訪問其他幾何圖形資訊。理論上,陰影(shadow)、反射(reflection)、折射(refraction)等為全域性光照(global illumination)效果,實際上,柵格化渲染系統可以使用預處理(如陰影貼圖(shadow mapping)、環境貼圖(environment mapping))去模擬這些效果。

全域性光照計算量大,一般也沒有特殊硬體加速(通常只使用CPU而非GPU),所以只適合離線渲染(offline rendering),例如3D Studio Max、Maya等工具。其中一個支援全域性光照的方法,稱為光線追蹤(ray tracing)。光線追蹤能簡單直接地支援陰影、反射、折射,實現起來亦非常容易。本文的例子裡,只用了數十行JavaScript程式碼(除canvas外不需要其他特殊外掛和庫),就能實現一個支援反射的光線追蹤渲染器。光線追蹤可以用來學習很多計算機圖形學的課題,也許比學習Direct3D/OpenGL更容易。現在,先介紹點理論吧。

光線追蹤

光柵化渲染,簡單地說,就是把大量三角形畫到螢幕上。當中會採用深度緩衝(depth buffer, z-buffer),來解決多個三角形重疊時的前後問題。三角形數目影響效能,但三角形在螢幕上的總面積才是主要瓶頸。

光線追蹤,簡單地說,就是從攝影機的位置,通過影像平面上的畫素位置(比較正確的說法是取樣(sampling)位置),發射一束光線到場景,求光線和幾何圖形間最近的交點,再求該交點的著色。如果該交點的材質是反射性的,可以在該交點向反射方向繼續追蹤。光線追蹤除了容易支援一些全域性光照效果外,亦不侷限於三角形作為幾何圖形的單位。任何幾何圖形,能與一束光線計算交點(intersection point),就能支援。

上圖(來源)顯示了光線追蹤的基本方式。要計算一點是否在陰影之內,也只須發射一束光線到光源,檢測中間有沒有障礙物而已。不過光源和陰影留待下回分解。

初試畫板

光線追蹤的輸出只是一個影像(image),所謂影像,就是二維顏色陣列。

要在瀏覽器內,用JavaScript生成一個影像,目前可以使用HTML 5的<canvas>。但現時Internet Explorer(直至版本8)還不支援<canvas>,其他瀏覽器如Chrome、Firefox、Opera等就可以。

以下是一個簡單的實驗,把每個象素填入顏色,左至右越來越紅,上至下越來越綠。

左邊的canvas定義如下:

1<canvas width="256" height="256" id="testCanvas"></canvas>

修改程式碼試試看

  • 把第三個pixels[i++] = 0 改為255 (即藍色全開)
  • 把第四個pixels[i++] = 255 改為128 (alpha=128)
  • 可以只修改兩個for迴圈裡面的程式碼,畫一個國際象棋棋盤麼?

這實驗說明,從canvas取得的影像資料canvas.getImageData(...).data是個一維陣列,該陣列每四個元素代表一個象素(按紅, 綠, 藍, alpha排列),這些象素在影像中從上至下、左至右排列。

解決實驗平臺的技術問題後,可開始從基礎類別開始實現。

基礎類

筆者使用基於物件(object-based)的方式編寫JavaScript。

三維向量

三維向量(3D vector)可謂CG裡最常用型別了。這裡三維向量用Vector3類實現,用(x, y, z)表示。 Vector3亦用來表示空間中的點(point),而不另建類。先看程式碼:

1234567891011121314151617Vector3 = function(x, y, z) { this.x = x; this.y = y; this.z = z; };Vector3.prototype = {copy : function() { return new Vector3(this.x, this.y, this.z); },length : function() { return Math.sqrt(this.x * this.x + this.y * this.y +

相關推薦

JavaScript計算機圖形()光線追蹤入門

系列簡介 記得小時候讀過一本關於計算機圖形學(computer graphics, CG)的入門書,從此就愛上了CG。本系列希望,採用很多人認識的JavaScript語言去分享CG,令更多人有機會接觸,並愛上CG。 本系列的特點之一,是讀者能在瀏覽

JavaScript計算機圖形(二)基本光源

上一篇介紹了簡單的光線追蹤,湊合了臨時用的光源去渲染效果。這次將講解三種基本光源,及一些背景理論。過分簡化的教材和現成API(OpenGL/Direct3D等)可能會做成一些錯誤理解。在此,希望文章能簡單之餘,又不失背後理論。讀者明白之後,可把概念簡化,或按實

Python資料》專案—線性迴歸分析入門之波士頓房價預測(二)

接上一部分,此篇將用tensorflow建立神經網路,對波士頓房價資料進行簡單建模預測。 二、使用tensorflow擬合boston房價datasets 1、資料處理依然利用sklearn來分訓練集和測試集。 2、使用一層隱藏層的簡單網路,試下來用當前這組超引數收斂較快,準確率也可以。 3、啟用函式

劍英陪你圖形()打通任督二脈

註定 輸出 加工 學生 odoo itblog 嘗試 固定 討論 1. 這是一個嘗試的系列,突發奇想覺得有聲音可能會更有趣,這個系列Blog都會出視頻有聲版。 這個系列主要是為了玩一玩代碼。 我覺得呢,寫程序是一件很有意思的事情,沒有必要搞得那麽苦大仇深。但是,卻總有那麽一

SQL數據挖掘之MADlib()——安裝

system wan 商品 ase 關聯規則挖掘 樹模型 ats 調用 ability   一、MADlib簡介    MADlib是Pivotal公司與伯克利大學合作的一個開源機器學習庫,提供了精確的數據並行實現、統計和機器學習方法對結構化和非結構化數據進行分析,主要目的

計算機圖形) 視頻顯示設備_1_CRT原理

http color size 安裝 ref p s 這一 計算機圖形學 指定 第 1 章 圖形系統概述 如今。計算機圖形學的作用與應用已經得到了廣泛承認。大量的圖形硬件和軟件系統已經應用 到了差點兒全部的領域。通用計算機甚至很多手持計算器也已經

計算機圖形(OpengGl版) 實驗(

結果展示: #include <windows.h> #include <GL/glut.h> #include <stdlib.h> #include <bits/stdc++.h> using namespace std; vo

計算機圖形實驗()--直線DDA演算法的實現

1. DDA演算法(數值微分法)原理:     1)網上或者計算機圖形學書本上有詳細介紹。     2)最核心的是選定(x2-x1)和(y2-y1)中較大者為步進方向。 2. 實現工具:     1) VS2017(C++)

計算機圖形python的turtle進行簡單的圖形繪製

【計算機圖形學】用python的turtle進行簡單的圖形繪製 python的turtle模組 繪製圖形 繪製點 繪製直線 繪製橢圓 繪製六邊形 繪製n次貝塞爾曲線 結語 python

計算機圖形 學習筆記():概述,直線掃描轉換演算法:DDA,中點畫線演算法,Bresenham演算法

前言 感謝中國農大 趙明老師的分享~ 現在我要為我自己走向遊戲程式設計打下基石~ 1 計算機圖形學概論 1.1 計算機圖形學課程簡介 《計算機圖形學》是計算機、地理資訊系統、應用數學、機械、建築等專業本科教學中的一門重要的專業基礎課 如影

計算機圖形02一一OpenGL 程式碼實現繪製條線

OpenGL 有一些自己的規則: 函式名的命名規範 是以gl開頭 之後每一組成詞的第一個字母大寫 例如glBegin , glCopyPixels 常量以GL開頭 後加_ 之後所以字母大寫 例如GL_2D , GL_RGB 資料型別它自帶了自己的資料型別 寫法 就是在我們之

計算機圖形考試-繪製條任意線型和線寬的直線。

程式設計繪製一條任意線型和線寬的直線。(線型、線寬可由使用者指定) 首先我們得了解一下線型和線寬的意思。 線型包括實線、虛線和點線等。線型的顯示在掃描轉換演算法中可通過畫素段的方法實現,即對各種虛線和點線,畫執行緒序沿線路徑輸出一些實線段(劃線),在每兩個劃線之間有一個空白

計算機圖形課程】.MFC基本繪圖函式使用方法

        這是最近我《計算機圖形學》課程實踐程式設計課介紹的相關知識,主要是想通過MFC C++繪圖,讓學生體會下圖形學相關的程式設計及簡單的圖形繪製,同時非常佩服學生的想象力,他們做得真的不錯。希望這篇基礎文章對你有所幫助吧!尤其是有這門課程的學生或程式設計愛好者,如

學習shader之前必須知道的東西之計算機圖形)渲染...

shader到底是幹什麼用的?shader的工作原理是什麼?         其實當我們對這個問題還很懵懂的時候,就已經開始急不可耐的要四處搜尋有關shader的資料,恨不得立刻上手寫一個出來。但看了一些資料甚至看了不少cg的語法之後,我們還是很迷茫,UNITY_MATRIX_MVP到底是個什麼矩陣?它和v

計算機圖形(四)_幾何變換_1_基本的二維幾何變換()

4 .幾何變換        使用線段和填充區等圖元來描述場景,並利用屬性來輔助這些圖元。我們給出了掃描線演算法,可以將圖元顯示在光柵裝置上。現在,再看看可用於物件重定位或改變大小的變換操作。這些操作也用於將世界座標系中的場景描述轉換為輸出裝置上顯示的觀察子程式中。另外,它

計算機圖形)DDA畫線演算法講解與原始碼

很早之前就想寫一個計算機圖形學系列的講解,可是隻寫了2篇,然後就擱置了很長一段時間,現在也算是有時間來繼續之前的想法了。 首先介紹一下演算法: 已知直線過端點P0(x0,y0),P1(x1,y1)的直線段的斜率K=(y1-y0)/(x1-x0),畫線的過程為:從x的

計算機圖形 讀書筆記() 基礎概念

寫個讀書筆記,一來作為字典以後可以查,二來記錄自己的理解。並沒有對每個知識點的詳細解釋,大部分只有主觀的定性的解釋。大量的配圖用的清華大學的PPT裡的圖,會不會有版權問題呀。。。。讓我刪我就刪。。一、顏色一種特定顏色的光可以由一種光譜表示,但這種表示方法太複雜,所以產生了其他

計算機圖形

概念: 研究通過計算機將資料轉換為圖形並在專門顯示裝置上顯示的原理方法和技術的學科 高質量的計算機圖形離不開高效能的計算機圖形硬體裝置。一個圖形系統通常是由圖形處理器,圖形輸入裝置和輸出裝置構成。 圖形顯示裝置* 圖形的輸出包括圖形的顯示和繪製。圖形的顯

實戰pandas資料分析()——使用者消費行為分析(python)

  CD商品訂單資料的分析總結。根據訂單資料(使用者的消費記錄),從時間維度和使用者維度,分析該網站使用者的消費行為。通過此案例,總結訂單資料的一些共性,能通過使用者的消費記錄挖掘出對業務有用的資訊。對其他產品的線上消費資料分析有一定的借鑑價值,能達到舉一反三的效果。 訂單交易資料分析 [

【3D計算機圖形】變換矩陣、歐拉角、四元數

遭遇 unit 額外 star 應該 detail 導致 print uic 【3D計算機圖形學】變換矩陣、歐拉角、四元數 旋轉矩陣、歐拉角、四元數主要用於:向量的旋轉、坐標系之間的轉換、角位移計算、方位的平滑插值計算。 一、變換矩陣: 首先要區分旋轉矩陣和變換矩陣: