1 | #pragma once
|
---|
2 | #include <vector>
|
---|
3 | #include "Parameters.h"
|
---|
4 | #include "Vector.hpp"
|
---|
5 | #include "Uniform.hpp"
|
---|
6 | #include "Radion.hpp"
|
---|
7 | #include "KDTree.hpp"
|
---|
8 | #include "xmlParser.h"
|
---|
9 |
|
---|
10 | class Material;
|
---|
11 | class TriangleMesh;
|
---|
12 | class Transformed;
|
---|
13 | class KDTree;
|
---|
14 | class RenderStrategy;
|
---|
15 |
|
---|
16 | /*!
|
---|
17 | \brief Main class for the PRM computation and usage application.
|
---|
18 | This class encapsulates all resources needed for computing PRMs and
|
---|
19 | using them in the final rendering. PRM resources may be generated,
|
---|
20 | saved to files, or restored.
|
---|
21 | */
|
---|
22 | class PathMapEffect
|
---|
23 | {
|
---|
24 | int NRADIONS;
|
---|
25 | int NCLUSTERS;
|
---|
26 | int DEPTHMAPRES;
|
---|
27 |
|
---|
28 | int testClusterId;
|
---|
29 |
|
---|
30 | friend class SubEntity;
|
---|
31 | friend class SubMesh;
|
---|
32 | friend class Entity;
|
---|
33 | friend class Mesh;
|
---|
34 | friend class DepthRenderStrategy;
|
---|
35 | friend class FinalCompositionRenderStrategy;
|
---|
36 |
|
---|
37 | float clusterSweepCurrentIndex; //!< test, cycling displayed entry point clusters
|
---|
38 |
|
---|
39 | //! pointer to global user-adjustable application parameters object
|
---|
40 | static Parameters* parameters;
|
---|
41 |
|
---|
42 | //! pointer to main DX device
|
---|
43 | LPDIRECT3DDEVICE9 device;
|
---|
44 | //! pointer to main DX effect
|
---|
45 | LPD3DXEFFECT effect;
|
---|
46 |
|
---|
47 | //! frame color buffer surface
|
---|
48 | //! saved before render-to-texture, and restored as the render target for the final rendering to the screen
|
---|
49 | LPDIRECT3DSURFACE9 frameColorBuffer;
|
---|
50 | //! frame depth buffer surface
|
---|
51 | //! saved before render-to-texture, and restored as the render target for the final rendering to the screen
|
---|
52 | LPDIRECT3DSURFACE9 frameDepthStencilBuffer;
|
---|
53 |
|
---|
54 | LPDIRECT3DTEXTURE9 depthMapTexture; //!< depth map texture
|
---|
55 | LPDIRECT3DSURFACE9 depthMapDepthStencilBuffer; //!< depth map texture's surface
|
---|
56 | LPDIRECT3DTEXTURE9 fakeTexture; //!< depth map dummy render texture
|
---|
57 | LPDIRECT3DSURFACE9 fakeSurface; //!< depth map dummy render surface
|
---|
58 |
|
---|
59 | LPDIRECT3DVERTEXBUFFER9 starterVertexBuffer; //!< vertex buffer with entry point positions, for entry point visualization
|
---|
60 |
|
---|
61 | LPDIRECT3DTEXTURE9 weightsTexture; //!< render target texture to which current entry point weights are computed
|
---|
62 | LPDIRECT3DSURFACE9 weightsSurface; //!< weights texture's surface
|
---|
63 | LPDIRECT3DTEXTURE9 sysMemWeightsTexture; //!< weights texture copy in system mem
|
---|
64 | LPDIRECT3DSURFACE9 sysMemWeightsSurface; //!< surface of weights texture copy in system mem
|
---|
65 | LPDIRECT3DTEXTURE9 radionTexture; //!< texture containing entry point data, input for weight computation
|
---|
66 | LPDIRECT3DSURFACE9 radionSurface; //!< entry point texture's surface
|
---|
67 |
|
---|
68 | LPDIRECT3DTEXTURE9 aggrWeightsTexture;
|
---|
69 | LPDIRECT3DSURFACE9 aggrWeightsSurface;
|
---|
70 |
|
---|
71 | KDTree* kdtree; //!< the kd-tree that contains the scene geometry in raytraceable format
|
---|
72 |
|
---|
73 | //! clever enum for supported final rendering methods
|
---|
74 | class Method{
|
---|
75 | unsigned int mid;
|
---|
76 | Method(unsigned int mid) {this->mid = mid;}
|
---|
77 | static const wchar_t * methodNames[10];
|
---|
78 | public:
|
---|
79 | Method(const Method& o) {mid = o.mid;}
|
---|
80 | const Method& operator=(const Method& o) {mid = o.mid; return *this;}
|
---|
81 | bool operator==(const Method& o) const {return mid == o.mid;}
|
---|
82 | bool operator!=(const Method& o) const {return mid != o.mid;}
|
---|
83 | const static Method PRM;
|
---|
84 | const static Method SHOWTEX;
|
---|
85 | const static Method LAST;
|
---|
86 | const Method& next() {mid = (mid + 1)%LAST.mid; return *this;}
|
---|
87 | const Method& prev() {mid = (mid + LAST.mid - 1)%LAST.mid; return *this;}
|
---|
88 | const wchar_t* getName() {return methodNames[mid];}
|
---|
89 | }method;
|
---|
90 | public:
|
---|
91 | void nextMethod() {method.next();}
|
---|
92 | void prevMethod() {method.prev();}
|
---|
93 | const wchar_t* getCurrentMethodName();
|
---|
94 |
|
---|
95 | //! camera
|
---|
96 | CFirstPersonCamera* camera;
|
---|
97 | //! primary light source (can be moved just like the real camera, and can be used as the camera)
|
---|
98 | CFirstPersonCamera* lightCamera;
|
---|
99 | private:
|
---|
100 |
|
---|
101 | //! xml data with material name -> texture reference
|
---|
102 | XMLNode xMaterials;
|
---|
103 |
|
---|
104 | std::vector<Mesh*> meshes;
|
---|
105 | //! vector of loaded textures (textures specified in mesh's material/bumpmap will be loaded here)
|
---|
106 | std::vector<LPDIRECT3DTEXTURE9> materialTextures;
|
---|
107 | std::vector<wchar_t*> materialTextureFileNames;
|
---|
108 | //! vector of ray trace materials
|
---|
109 | std::vector<Material*> rayTraceMaterials;
|
---|
110 |
|
---|
111 | //! for materials with no texture we will render with this texture
|
---|
112 | LPDIRECT3DTEXTURE9 emptyTexture;
|
---|
113 |
|
---|
114 | LPDIRECT3DTEXTURE9 shipBrdfTexture;
|
---|
115 | LPD3DXMESH shipMesh;
|
---|
116 | D3DXMATRIX shipPos;
|
---|
117 | D3DXMATRIX shipPosInverse;
|
---|
118 | int cruiseLoop;
|
---|
119 | float loopPos;
|
---|
120 |
|
---|
121 | //! private method that loads a mesh and its textures
|
---|
122 | void loadMesh(DWORD fileType, LPCWSTR fileName, LPCWSTR ogreName, int prmAtlasSize, const char* name, int dividePcs, bool generateUV, bool generateTBN, unsigned int originalAtlasTexCoordIndex);
|
---|
123 |
|
---|
124 | //! private method to load a texture
|
---|
125 | LPDIRECT3DTEXTURE9 loadTexture(LPCWSTR fileName, Material** rayTraceMaterial=NULL);
|
---|
126 |
|
---|
127 | //! private method make a CPU Material out of a D3D texture
|
---|
128 | Material* createRayTraceMaterial(LPDIRECT3DTEXTURE9 texture);
|
---|
129 |
|
---|
130 | //! release material texture resources
|
---|
131 | void releaseTextures();
|
---|
132 | //! release mesh resources
|
---|
133 | void releaseMeshes();
|
---|
134 | //! release entities
|
---|
135 | void releaseEntities();
|
---|
136 |
|
---|
137 | //! struct that represents a virtual world object: a mesh and a model-world transformation matrix
|
---|
138 |
|
---|
139 | //! renders a full screen quad, invoking the pixel shader for all pixels
|
---|
140 | //! used for rendering the environment map to the background
|
---|
141 | void renderFullScreen(float depth = 0.0f);
|
---|
142 |
|
---|
143 | //! vector of virtual world objects
|
---|
144 | std::vector<Entity*> entities;
|
---|
145 | public:
|
---|
146 | //! constructor: allocates all resources
|
---|
147 | PathMapEffect(LPDIRECT3DDEVICE9 device,
|
---|
148 | char* prmDirectory,
|
---|
149 | char* meshDirectory,
|
---|
150 | char* mediaDirectory,
|
---|
151 | char* levelFileName,
|
---|
152 | char* materialFileName,
|
---|
153 | bool segmentMeshes,
|
---|
154 | bool computePRM,
|
---|
155 | bool uniformSampling,
|
---|
156 | bool atlasGen,
|
---|
157 | unsigned int nEntryPoints,
|
---|
158 | unsigned int nClusters,
|
---|
159 | unsigned int depthMapResolution);
|
---|
160 |
|
---|
161 | wchar_t prmDirectory[256];
|
---|
162 | wchar_t meshDirectory[256];
|
---|
163 | wchar_t mediaDirectory[256];
|
---|
164 | wchar_t levelFileName[256];
|
---|
165 | wchar_t materialFileName[256];
|
---|
166 | bool SEGMENTMESHES;
|
---|
167 | bool UNIFORMSAMPLING;
|
---|
168 |
|
---|
169 | //! destructor: releases all resources
|
---|
170 | ~PathMapEffect(void);
|
---|
171 |
|
---|
172 | //! renders the scene using the currently selected method
|
---|
173 | void render();
|
---|
174 |
|
---|
175 | //! renders the scene, using the PRMs for indirect illumination
|
---|
176 | void renderWithPRM();
|
---|
177 |
|
---|
178 | //! displays a part of a PRM texture
|
---|
179 | // void showPRMTexture();
|
---|
180 |
|
---|
181 | //! moves the virtual world objects (camera, light)
|
---|
182 | void move(float fElapsedTime);
|
---|
183 |
|
---|
184 | LRESULT handleMessage( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
|
---|
185 |
|
---|
186 | //! adds controls for the user-adjustable application parameters
|
---|
187 | static void addUiParameters(Parameters* parameters);
|
---|
188 | static void setUiParameterDefaults(Parameters* parameters);
|
---|
189 |
|
---|
190 | LPDIRECT3DDEVICE9 getDevice() {return device;}
|
---|
191 |
|
---|
192 | const wchar_t* getWeightsString();
|
---|
193 | private:
|
---|
194 | float* weights; //!< the array of averaged cluster weights
|
---|
195 | unsigned int* clusterLenghts; //!< array thet contasins the number of entry points in every cluster (entry points are stored continously [bushStarters, starterVertexBuffer])
|
---|
196 |
|
---|
197 | float sumSurfaceArea; //!< summed surface area of all entities
|
---|
198 |
|
---|
199 | void createPRMTextures(); //!< allocates PRM resources for every entity
|
---|
200 |
|
---|
201 | //! generates a random direction (cosine distribution) near a normal vector
|
---|
202 | static void sampleShootingDiffuseDirection(int depth, const Vector& normal, Vector& outDir);
|
---|
203 | //! generates a random direction an the unit sphere
|
---|
204 | static void sampleSphereDirection(Vector& outDir);
|
---|
205 |
|
---|
206 | //! finds a random entry point (all entities considered with equal probability)
|
---|
207 | void sampleSurfaceRadion(Radion& starter);
|
---|
208 | //! finds a random entry point (all entities considered with probability proporstional to surface area)
|
---|
209 | void sampleSurfaceRadionUniform(Radion& starter);
|
---|
210 |
|
---|
211 | //! shoot virtual light sources from original entry point and add them to the vector
|
---|
212 | void shootRadionBush(Radion& starter, std::vector<Radion>& bushRadions);
|
---|
213 |
|
---|
214 | //! sort radions into initial, uniform length clusters
|
---|
215 | int clusterRadions(Radion* partition, int psize, char axis);
|
---|
216 |
|
---|
217 | //! use K-means clustering to cluster radions
|
---|
218 | void clusterRadionsKMeans();
|
---|
219 |
|
---|
220 | //! perform computaions: generate entry points, render PRMs
|
---|
221 | void precompute();
|
---|
222 |
|
---|
223 | int getNBushes() {return NRADIONS; }
|
---|
224 | int getNClusters() {return NCLUSTERS;}
|
---|
225 |
|
---|
226 | //! entry points
|
---|
227 | std::vector<Radion> bushStarters;
|
---|
228 |
|
---|
229 | int rayId;
|
---|
230 | Ray ray;
|
---|
231 | HitRec hitRec;
|
---|
232 |
|
---|
233 | //! fill 'radionsTexture' from 'bushStarters'
|
---|
234 | void uploadRadions();
|
---|
235 | //! fill *pData (will point to locked 'starterVertexBuffer') from 'bushStarters'
|
---|
236 | void fillRadionPosArray(void* pData);
|
---|
237 |
|
---|
238 | public:
|
---|
239 | //! store all precomputed data for the scene in folder prm
|
---|
240 | void savePathMaps();
|
---|
241 | //! restore all precomputed data for the scene from folder prm
|
---|
242 | void loadPathMaps();
|
---|
243 |
|
---|
244 | void exportEntityData();
|
---|
245 |
|
---|
246 | void loadScene(const char* sceneFileName);
|
---|
247 | void saveScene(const char* sceneFileName);
|
---|
248 |
|
---|
249 | void renderScene(const RenderStrategy& renderStrategy);
|
---|
250 |
|
---|
251 | wchar_t* getCruiseLoop();
|
---|
252 | };
|
---|