范曾,張建偉
(四川大學計算機學院,成都610065)
幾十年來,復雜植物的幾何建模一直是計算機圖形學面臨的一個挑戰。其中,真實、實時的樹木建模與渲染是一個相當困難的部分。因為樹木是戶外場景的主要組成部分,并且具有復雜的拓撲結構和幾何形狀,需要大量的圖元才能形成令人信服的視覺效果。樹冠內樹枝和樹葉的重疊交錯,以及樹木在結構上的自相似性,使樹木模型的生成變得復雜。
為了避免這些困難,此類三維模型的生成通常基于程序方法,如Lindenmayer 系統[1],該系統通過形式語言的描述來創建模型,見圖1。程序樹模型在計算機圖形學中很受歡迎,因為它們能夠從一組輸入參數生成各種輸出樹,并模擬植物與環境的交互,以便在虛擬場景中真實地放置樹木。
不幸的是,要模擬特定的樹或給定的樹種,通常必須手動地調整許多參數。這使得建模的工作人員以及藝術家們背負著很大的創作負擔。并且,大規模植物的幾何復雜性仍然超過了當前計算機硬件的渲染能力。為了解決這個問題,研究者們已經開發了幾種策略:①簡化網格以減少多邊形的數量;②用更基本的幾何體(如點、線、圓柱體)替換復雜多邊形;③用紋理或billboard 替換3D 幾何體。這些方法都有效地提高了繪制大范圍森林的效率。在飛行模擬機中,我們的樹木模型是按照植物學規則構建的,它反映了植物的生長過程及其空間占有率。其中,樹木的樹枝由非常簡單的圓柱體表示,足以用于沉浸式的視景視圖中。

圖1 Lindenmayer系統
經典的樹建模是基于規則或使用建模過程的。雖然Prusinkiewicz 和Lindenmayer 的L 系統[1]中的形式規則適用于初始狀態,但大多數過程方法使用參數化算法,如Oppenheimer[2]、de Reffye[3]、Holton[4]、Weber 和Penn[5]。這些算法也對規則進行編碼,但用的是更具體的概念。Lintermann 和Deussen[6]的xfrog 系統試圖將這兩種方法結合起來。
在經典的L 系統中,規則基礎必須由用戶編寫。由于規則作用于局部,所以值的細微差異可能會導致整體形狀的變化。這樣的方式使得建模非常麻煩。從那時起,人們提出了L-系統的各種擴展,例如Prusinkiewicz 和Lindenmayer[7]的 參 數 化、Mech 和Prusinkiewicz[8]的開放式,和Prusinkiewicz 等人[9]的微分L 系統。這些擴展可以創建各種效果,但也會產生附加參數。Prusinkiewicz 等人[10]為L 系統提供了一個建模接口,以增強建模的簡便性,但仍有大量參數需要用戶定義。
程序性方法通常僅限于產生數量有限的形狀。它們還可以限制用戶可調參數的數量。然而,隨著模型復雜性的增加,這個數量也會增加。雖然Oppenheimer[2]只使用了一些基本參數,但后來的方法,如Weber 和Penn[5]提出的方法有幾十個參數。
在xfrog 系統中,使用一個簡單的規則系統來組合過程元素,這樣可以更快地進行建模。但是,參數的數量仍然很大。Ijiri 等人[11]使用基于植物學規則的交互式編輯器來創建植物模型。雖然這些編輯允許高效地制作花和葉序,但在制作復雜樹木方面并不出彩。Okabe 等人[12]提出了一種基于草圖創建樹木的接口。在這種方法中,用戶可以繪制樹骨架的輪廓及其形狀。然而,許多參數必須調整以達到特定的物種。
基于粒子的方法[13]在與自然生長相反的方向構造樹骨架。最初,粒子是在樹冠(球形或圓錐形)的樹葉位置生成的。模擬流動的方法是,以小步重復移動粒子到其最近的鄰居和根,當粒子非常接近時合并粒子。獲得的粒子軌跡形成樹骨架,隨后用于擠出可渲染幾何體。為了將粒子引導到地面,Rodkaew 等人使用靜態目標點和最近鄰吸引力,這會在粒子軌跡中產生急轉彎,并嚴重限制建模的通用性。
粒子流算法對于從運動捕捉到的樹枝尖端[14]或激光掃描[15]重建樹也很有用。Xu 和Mold[16]提出了一種自頂向下的方法來構造不規則樹模型。一個加權圖是由一組隨機生成的點在一個用戶繪制的樹shell 的旋轉中構造的,其中一個點被指定為根節點,而其他節點的隨機選擇則指定端點。找到從各個端點到根節點的最短路徑,并用于構造樹骨架。此過程將重復多次,其端點來自上一次迭代服務的端點在下一次迭代中。這種方法比粒子流算法需要更多的內存,因為在每次迭代中都會構造出一個具有多個節點甚至更多邊的新圖。在他們使用引導向量的方法[17]的后期擴展中,作者使用了單個圖,但是高空間復雜度仍然是該方法的主要限制。
Reche Martinez 等人[18]描述了一種非常精確但復雜的基于圖像的建模方法。在這種方法中,使用一組注冊的照片來確定給定樹的體積形狀。體積被分成單元塊,對于每個單元塊,用一組紋理計算出有效的視覺表示。完整的紋理集代表了樹。然而,這種方式需要數十兆字節的紋理空間。另外,在不同的光照條件下也不容易顯示樹,因為光照已經包含在紋理中。
另一類不同的樹木合成方法是資源競爭(如光、空氣、水等)視為樹木生長的驅動機制。其中提出基于局部生長條件的模型結構自組織生長是Pa?ubicki 等人[19]的關鍵貢獻。
本文的樹木建模基于Pa?ubicki 等人的自組織建模方式,將樹描述為一個分層組織的模塊化結構。一片或多片葉子附著在莖上的那一點叫做節。莖在兩個節之間的部分是節間。在每片葉的腋部形成一個側芽,即支撐葉的莖和葉柄之間的有角空間。一個節間與附生的葉和芽形成一個變位異構體。
一個芽可能有四種不同的命運:產生一個新的變位異構體,產生一朵花,保持休眠(保持將來生長的可能性)或死亡。變位異構體可以連續或有周期地產生。溫帶氣候樹木的生長是有周期性的,受季節循環的調節。在一次生長(溫帶氣候樹木的春天)中產生的一系列變位異構體形成一個嫩芽。芽軸由位于芽端的頂芽產生。主干由幼苗的頂芽發育而來,軸序為0。軸序為n 的側芽生長之后將會成為它產生的軸序+1 的頂芽。
生長方式分為兩類:
(1)連年持續產生的嫩枝呈線性排列,形成單枝分枝結構。
(2)樹木發育的主要推力轉移到側枝,頂芽產生一朵花或死亡。這樣將會導致共軸分枝。新的分枝可以在同一季節產生(即與支撐它們的莖形成的同一季節)。
通過模擬樹木的生長過程,創建一個樹形結構。
本文將樹木生長所需要的環境資源(如陽光、水分、空氣等)用隨機生成的3D 資源點表示。在程序運行之處,用C++的隨機函數生成指定數量的3D 資源點。隨后,將資源點構建為KD-Tree。我們假設每個芽被一個半徑為r 的球形占據區所包圍,并且每個芽有一個感知角度為θ、距離為R 的圓錐形感知體。在每一次生長迭代的過程中,根據構建的KD-Tree,從3D資源點集中刪除任何芽的占用區域內的點,然后芽再去爭奪剩余的資源點。用這種方式計算每個芽周圍空間的可用性,同時依據空間定殖的方法計算芽的最佳生長方向。其中,若芽周圍空間的可用性為0,則芽不生長;若芽周圍空間的可用性為1,則芽可按照計算得出的最佳生長方向生長。
在這個階段,通過上一節中計算得到的芽周圍空間的可用性決定芽的命運。由于目前尚不清楚自然界的根尖控制是通過資源競爭、激素控制還是二者都有,這里采用Pa?ubicki 等人實現的擴展模型進行資源分配。
該模型通過控制生長誘導資源向芽的分配來調節分枝,通過考慮分支點處(即芽)接收到的資源點數量分配縱向流動的資源。該算法氛圍兩個步驟:①到達芽的資源是流動的,累積值存儲在節間。②累積值決定了該過程要分配的資源量:Resbase=αCbase,其中α是比例系數。到達分支點的資源按照公式(1)分布在連續的主軸Cm和橫向分枝Cl之間。

其中,ε∈[0,1]控制資源是否偏向主軸(ε>0.5),還是偏向側枝(ε<0.5)。到達一個芽的資源量Res 的整數部分決定了這個芽產生的變位異構體的數量:n=。
默認情況下,新幼芽是按芽所指的方向生長的。頂芽的方向與它的支撐節間的方向一致。側芽的方向由葉序和芽與親本節間的分枝角度決定。形成一個新芽的連續變位體的方向受到兩個因素的影響:由環境決定的最佳生長方向和重力因素。因此,變位異構體的實際生長方向計算為上述三種方向的加權和。
隨后,通過計算得出該芽在一次迭代生長之后的半徑與長度,按照相應比例對替代樹枝的圓柱體進行放縮,可得到新生長出來的樹枝。
該程序運行的界面效果如圖2、3 所示。點擊“Add Attr Pt Cloud”按鈕生成隨機的3D 資源點,繪制在窗口上,見圖2。

圖2 隨機資源點圖示
隨后設置不同參數(如樹枝半徑、迭代生長次數等),點擊“Iterate Tree”按鈕,每次點擊樹木會生長一次,如圖3。

圖3 動態生成樹
經過幾十年的發展,森林的建模算法已經有了巨大的進步。本文通過研究最近30 年內樹木的建模方式,對各種方式進行分析,結合飛行模擬視景的實際情況,基于自組織思想的建模方法,并利用OpenGL、Dear Imgui、glfw 以及glad 庫編程實現了單顆樹木建模的動態演示。該應用程序具備一定的可擴展性。然而,由于飛行模擬機這類大規模的視景需要在短時間內生成成千上萬棵樹,一個可行的優化改進方向是利用OpenGL 的Compute Shader 進行并行化處理。針對繪制效率的問題,還需要繼續改進研究。