VirtualBox

source: vbox/trunk/src/VBox/HostServices/SharedOpenGL/crserverlib/server_projmatrix.cpp@ 78263

最後變更 在這個檔案從78263是 78263,由 vboxsync 提交於 6 年 前

Config.kmk,GuestHost\OpenGL,HostServices\SharedOpenGL: Fix a bunch of compiler warnings and enable them again

  • 屬性 svn:eol-style 設為 native
  • 屬性 svn:keywords 設為 Id Revision
檔案大小: 13.5 KB
 
1/* Copyright (c) 2001, Stanford University
2 * All rights reserved
3 *
4 * See the file LICENSE.txt for information on redistributing this software.
5 */
6
7#include "server_dispatch.h"
8#include "server.h"
9#include "cr_error.h"
10#include "state/cr_statetypes.h"
11#include "cr_mem.h"
12#include "cr_string.h"
13
14/*
15 * This file provides implementations of the basic OpenGL matrix functions.
16 * We often need to twiddle with their operation in order to make tilesorting
17 * and non-planar projections work.
18 */
19
20
21
22/*
23 * Determine which view and projection matrices to use when in stereo mode.
24 * Return 0 = left eye, 1 = right eye.
25 */
26int crServerGetCurrentEye(void)
27{
28 if (cr_server.currentEye != -1) {
29 /* current eye was specified by tilesort SPU */
30 return cr_server.currentEye;
31 }
32 else {
33 /* we have a quad-buffered window and we're watching glDrawBuffer */
34 GLenum drawBuffer = cr_server.curClient->currentCtxInfo->pContext->buffer.drawBuffer;
35 int eye = drawBuffer == GL_BACK_RIGHT || drawBuffer == GL_FRONT_RIGHT
36 || drawBuffer == GL_RIGHT;
37 return eye;
38 }
39}
40
41
42void SERVER_DISPATCH_APIENTRY crServerDispatchLoadMatrixf( const GLfloat *m )
43{
44 const GLenum matMode = cr_server.curClient->currentCtxInfo->pContext->transform.matrixMode;
45
46 crStateLoadMatrixf( m );
47
48 if (matMode == GL_MODELVIEW && cr_server.viewOverride) {
49 int eye = crServerGetCurrentEye();
50 crServerApplyViewMatrix(&cr_server.viewMatrix[eye]);
51 }
52 else {
53 cr_server.head_spu->dispatch_table.LoadMatrixf( m );
54 }
55}
56
57
58void SERVER_DISPATCH_APIENTRY crServerDispatchLoadMatrixd( const GLdouble *m )
59{
60 const GLenum matMode = cr_server.curClient->currentCtxInfo->pContext->transform.matrixMode;
61
62 crStateLoadMatrixd( m );
63
64 if (matMode == GL_MODELVIEW && cr_server.viewOverride) {
65 int eye = crServerGetCurrentEye();
66 crServerApplyViewMatrix(&cr_server.viewMatrix[eye]);
67 }
68 else {
69 cr_server.head_spu->dispatch_table.LoadMatrixd( m );
70 }
71}
72
73
74void SERVER_DISPATCH_APIENTRY crServerDispatchMultMatrixf( const GLfloat *m )
75{
76 const GLenum matMode = cr_server.curClient->currentCtxInfo->pContext->transform.matrixMode;
77
78 if (matMode == GL_PROJECTION && cr_server.projectionOverride) {
79 /* load the overriding projection matrix */
80 int eye = crServerGetCurrentEye();
81 crStateLoadMatrix( &cr_server.projectionMatrix[eye] );
82 }
83 else {
84 /* the usual case */
85 crStateMultMatrixf( m );
86 cr_server.head_spu->dispatch_table.MultMatrixf( m );
87 }
88}
89
90
91void SERVER_DISPATCH_APIENTRY crServerDispatchMultMatrixd( const GLdouble *m )
92{
93 const GLenum matMode = cr_server.curClient->currentCtxInfo->pContext->transform.matrixMode;
94
95 if (matMode == GL_PROJECTION && cr_server.projectionOverride) {
96 /* load the overriding projection matrix */
97 int eye = crServerGetCurrentEye();
98 crStateLoadMatrix( &cr_server.projectionMatrix[eye] );
99 }
100 else {
101 /* the usual case */
102 crStateMultMatrixd( m );
103 cr_server.head_spu->dispatch_table.MultMatrixd( m );
104 }
105}
106
107
108
109void SERVER_DISPATCH_APIENTRY crServerDispatchLoadIdentity( void )
110{
111 const GLenum matMode = cr_server.curClient->currentCtxInfo->pContext->transform.matrixMode;
112
113 crStateLoadIdentity();
114
115 if (matMode == GL_MODELVIEW && cr_server.viewOverride) {
116 int eye = crServerGetCurrentEye();
117 crServerApplyViewMatrix(&cr_server.viewMatrix[eye]);
118 }
119 else {
120 cr_server.head_spu->dispatch_table.LoadIdentity( );
121 }
122}
123
124
125
126/*
127 * The following code is used to deal with vertex programs.
128 * Basically, vertex programs might not directly use the usual
129 * OpenGL projection matrix to project vertices from eye coords to
130 * clip coords.
131 *
132 * If you're using Cg then the vertex programs it generates will have
133 * some comments that we can scan to figure out which program parameters
134 * contain the projection matrix.
135 * In this case, look at the Cg program code for a string like
136 * "ModelViewProj". Then set the crserver's 'vertprog_projection_param'
137 * config option to this name.
138 *
139 * If you're not using Cg, you may have to tell Chromium which program
140 * parameters contain the projection matrix.
141 * In this case, look at the OpenGL application's vertex program code to
142 * determine which program parameters contain the projection matrix.
143 * Then set the crserver's 'vertprog_projection_param' config option to
144 * the number of the parameter which holds the first row of the matrix.
145 *
146 * Yup, this is complicated.
147 *
148 */
149
150
151static void matmul(GLfloat r[16], const GLfloat p[16], const GLfloat q[16])
152{
153 GLfloat tmp[16];
154 int i, j, k;
155 for (i = 0; i < 4; i++) {
156 for (j = 0; j < 4; j++) {
157 GLfloat dot = 0.0;
158 for (k = 0; k < 4; k++) {
159 dot += p[i+4*k] * q[k+4*j];
160 }
161 tmp[i+4*j] = dot;
162 }
163 }
164 for (i = 0; i < 16; i++)
165 r[i] = tmp[i];
166}
167
168
169static CRServerProgram *
170LookupProgram(GLuint id)
171{
172 CRServerProgram *prog = (CRServerProgram *)crHashtableSearch(cr_server.programTable, id);
173 if (!prog) {
174 prog = (CRServerProgram *) crAlloc(sizeof(CRServerProgram));
175 if (!prog)
176 return NULL;
177 prog->id = id;
178 prog->projParamStart = cr_server.vpProjectionMatrixParameter;
179 crHashtableAdd(cr_server.programTable, id, prog);
180 }
181 return prog;
182}
183
184
185void SERVER_DISPATCH_APIENTRY
186crServerDispatchProgramLocalParameter4fARB(GLenum target, GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
187{
188#if 0
189 if (target == GL_VERTEX_PROGRAM_ARB) {
190 CRServerProgram *prog = LookupProgram(cr_server.currentProgram);
191
192 if (prog && prog->projParamStart != -1) {
193 if (index >= (GLuint) prog->projParamStart && index <= (GLuint) prog->projParamStart + 3) {
194 /* save the parameters as rows in the matrix */
195 const int i = index - prog->projParamStart;
196 prog->projMat[4*0+i] = x;
197 prog->projMat[4*1+i] = y;
198 prog->projMat[4*2+i] = z;
199 prog->projMat[4*3+i] = w;
200 }
201
202 /* When we get the 4th row (row==3) of the projection matrix we can
203 * then pre-multiply it by the base matrix and update the program
204 * parameters with the new matrix.
205 */
206 if (index == (GLuint) (prog->projParamStart + 3)) {
207 const CRMuralInfo *mural = cr_server.curClient->currentMural;
208 const GLfloat *baseMat = (const GLfloat *) &(mural->extents[mural->curExtent].baseProjection);
209 int i;
210 GLfloat mat[16];
211
212 /* pre-mult the projection matrix by the base projection */
213 matmul(mat, baseMat, prog->projMat);
214 /* update the program parameters with the new matrix */
215 for (i = 0; i < 4; i++) {
216 cr_server.head_spu->dispatch_table.ProgramLocalParameter4fARB(target, index + i - 3, mat[4*0+i], mat[4*1+i], mat[4*2+i], mat[4*3+i]);
217 }
218 return; /* done */
219 }
220 }
221 }
222#endif
223
224 /* if we get here, pass the call through unchanged */
225 cr_server.head_spu->dispatch_table.ProgramLocalParameter4fARB(target, index, x, y, z, w);
226}
227
228
229void SERVER_DISPATCH_APIENTRY
230crServerDispatchProgramLocalParameter4dARB(GLenum target, GLuint index, GLdouble x, GLdouble y, GLdouble z, GLdouble w)
231{
232 crServerDispatchProgramLocalParameter4fARB(target, index, (GLfloat) x, (GLfloat) y, (GLfloat) z, (GLfloat) w);
233}
234
235
236void SERVER_DISPATCH_APIENTRY
237crServerDispatchProgramParameter4fNV(GLenum target, GLuint index, GLfloat x, GLfloat y, GLfloat z, GLfloat w)
238{
239#if 0
240 if (target == GL_VERTEX_PROGRAM_NV) {
241 CRServerProgram *prog = LookupProgram(cr_server.currentProgram);
242
243 if (prog && prog->projParamStart != -1) {
244 if (index >= (GLuint) prog->projParamStart && index <= (GLuint) prog->projParamStart + 3) {
245 /* save the parameters as rows in the matrix */
246 const int i = index - prog->projParamStart;
247 prog->projMat[4*0+i] = x;
248 prog->projMat[4*1+i] = y;
249 prog->projMat[4*2+i] = z;
250 prog->projMat[4*3+i] = w;
251 }
252
253 /* When we get the 4th row (row==3) of the projection matrix we can
254 * then pre-multiply it by the base matrix and update the program
255 * parameters with the new matrix.
256 */
257 if (index == (GLuint) (prog->projParamStart + 3)) {
258 const CRMuralInfo *mural = cr_server.curClient->currentMural;
259 const GLfloat *baseMat = (const GLfloat *) &(mural->extents[mural->curExtent].baseProjection);
260 int i;
261 GLfloat mat[16];
262
263 /* pre-mult the projection matrix by the base projection */
264 matmul(mat, baseMat, prog->projMat);
265 /* update the program parameters with the new matrix */
266 for (i = 0; i < 4; i++) {
267 cr_server.head_spu->dispatch_table.ProgramParameter4fNV(target, index + i - 3, mat[4*0+i], mat[4*1+i], mat[4*2+i], mat[4*3+i]);
268 }
269 return; /* done */
270 }
271 }
272 }
273#endif
274
275 /* if we get here, pass the call through unchanged */
276 cr_server.head_spu->dispatch_table.ProgramParameter4fNV(target, index, x, y, z, w);
277}
278
279
280void SERVER_DISPATCH_APIENTRY
281crServerDispatchProgramParameter4dNV(GLenum target, GLuint index, GLdouble x, GLdouble y, GLdouble z, GLdouble w)
282{
283 crServerDispatchProgramParameter4fNV(target, index, (GLfloat) x, (GLfloat) y, (GLfloat) z, (GLfloat) w);
284}
285
286
287void SERVER_DISPATCH_APIENTRY
288crServerDispatchProgramStringARB(GLenum target, GLenum format, GLsizei len, const GLvoid *string)
289{
290 if (target == GL_VERTEX_PROGRAM_ARB &&
291 cr_server.vpProjectionMatrixVariable != NULL) {
292 /* scan the program string looking for 'vertprog_projection'
293 * If the program was generated by Cg, the info we want will look
294 * something like this:
295 * #var float4x4 ModelViewProj : : c[0], 4 : 1 : 1
296 */
297 CRServerProgram *prog = LookupProgram(cr_server.currentProgram);
298 CRASSERT(prog);
299 if (prog) {
300 const char *varPos, *paramPos;
301 varPos = crStrstr((const char *) string, cr_server.vpProjectionMatrixVariable);
302 if (varPos) {
303 paramPos = crStrstr(varPos, "c[");
304 if (paramPos) {
305 char number[10];
306 int i = 0;
307 paramPos += 2; /* skip "c[" */
308 while (crIsDigit(paramPos[i])) {
309 number[i] = paramPos[i];
310 i++;
311 }
312 number[i] = 0;
313 prog->projParamStart = crStrToInt(number);
314 }
315 }
316 else {
317 crWarning("Didn't find %s parameter in vertex program string",
318 cr_server.vpProjectionMatrixVariable);
319 }
320 }
321 }
322
323 /* pass through */
324 crStateProgramStringARB(target, format, len, string);
325 cr_server.head_spu->dispatch_table.ProgramStringARB(target, format, len, string);
326}
327
328
329void SERVER_DISPATCH_APIENTRY
330crServerDispatchLoadProgramNV(GLenum target, GLuint id, GLsizei len, const GLubyte *string)
331{
332 if (target == GL_VERTEX_PROGRAM_NV &&
333 cr_server.vpProjectionMatrixVariable != NULL) {
334 /* scan the program string looking for 'vertprog_projection'
335 * If the program was generated by Cg, the info we want will look
336 * something like this:
337 * #var float4x4 ModelViewProj : : c[0], 4 : 1 : 1
338 */
339 CRServerProgram *prog = LookupProgram(id);
340 CRASSERT(prog);
341 if (prog) {
342 const char *varPos, *paramPos;
343 varPos = crStrstr((const char *) string, cr_server.vpProjectionMatrixVariable);
344 if (varPos) {
345 paramPos = crStrstr(varPos, "c[");
346 if (paramPos) {
347 char number[10];
348 int i = 0;
349 paramPos += 2; /* skip "c[" */
350 while (crIsDigit(paramPos[i])) {
351 number[i] = paramPos[i];
352 i++;
353 }
354 number[i] = 0;
355 prog->projParamStart = crStrToInt(number);
356 }
357 }
358 else {
359 crWarning("Didn't find %s parameter in vertex program string",
360 cr_server.vpProjectionMatrixVariable);
361 }
362 }
363 }
364
365 /* pass through */
366 crStateLoadProgramNV(target, id, len, string);
367 cr_server.head_spu->dispatch_table.LoadProgramNV(target, id, len, string);
368}
369
370
371void SERVER_DISPATCH_APIENTRY
372crServerDispatchBindProgramARB(GLenum target, GLuint id)
373{
374 id = crServerTranslateProgramID(id);
375
376 if (target == GL_VERTEX_PROGRAM_ARB) {
377 CRServerProgram *prog = LookupProgram(id);
378 (void) prog;
379 cr_server.currentProgram = id;
380 }
381
382 /* pass through */
383 crStateBindProgramARB(target, id);
384 cr_server.head_spu->dispatch_table.BindProgramARB(target, id);
385}
386
387
388void SERVER_DISPATCH_APIENTRY
389crServerDispatchBindProgramNV(GLenum target, GLuint id)
390{
391 if (target == GL_VERTEX_PROGRAM_NV) {
392 CRServerProgram *prog = LookupProgram(id);
393 (void) prog;
394 cr_server.currentProgram = id;
395 }
396 /* pass through */
397 crStateBindProgramNV(target, id);
398 cr_server.head_spu->dispatch_table.BindProgramNV(target, id);
399}
注意: 瀏覽 TracBrowser 來幫助您使用儲存庫瀏覽器

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette