Précédent   Forum des professionnels en informatique > Applications > Développement 2D, 3D et Jeux > API graphiques > DirectX
DirectX Forum d'entraide sur le développement avec DirectX. Avant de poster -> FAQ DirectX
Partagez cette discussion sur d'autres réseaux sociaux : Viadeo Twitter Google Facebook Digg Delicious MySpace Yahoo
Réponse Proposer ce sujet en actualité
 
Outils de la discussion
Publicité
'
Vieux 27/07/2011, 10h22   #1
Invité régulier
 
Inscription : septembre 2007
Messages : 20
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 20
Points : 6
Points : 6
Par défaut [DX9] Bypasser la matrice de vue

Bonjour !

Dans le cadre du portage d'un (petit) programme OpenGL en DirectX, je rencontre un problème avec la matrice de vue (viewmatrix).

En effet le principe du programme est de calculer une matrice de projection off-axis "à la main" en calculant en fonction de la taille de l'écran le frustum de vue. Couplé à un système de headtracking cela permet d'avoir la scène en fonction du point de vue de l'utilisateur.

Seulement en DirectX j'ai un petit problème : je ne sais pas quoi faire de la matrice de vue qui n'existe pas en OpenGL. Je sais qu'en OpenGL je ne devais surtout pas utiliser la fonction gluLookAt() qui détruisait tout le travail précédent.
En gros dans le calcul de la matrice de projection la position des yeux est prise en compte est c'est elle la position de la caméra.
Seulement quoi que je fasse, que je tente de charger une simple matrice identité dans la matrice de vue ou bien carrément ne l'utilise pas, je ne vois rien à l'écran à part ma couleur de fond !

Quelqu'un saurait-il comment gérer la matrice de vue dans ce cas là ?

Merci d'avance

Le code source du calcul en question (mmWidth et mmHeight sont la largeur et la hauteur de l'écran en mm) :
Code :
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
///*********CALCUL DE LA MATRICE DE PROJECTION**********
		D3DXMATRIX matProjection;
 
		//Bords de l'écran
		D3DXVECTOR3 pa(- mmWIDTH / 2.0f,-mmHEIGHT/2.0f,0.0f);
		D3DXVECTOR3 pb(mmWIDTH / 2.0f,-mmHEIGHT/2.0f,0.0f);
		D3DXVECTOR3 pc(- mmWIDTH / 2.0f,mmHEIGHT/2.0f,0.0f);
 
		//Position des yeux
		D3DXVECTOR3 pe(0.0f,0.0f,-50.0f);
 
		//Base orthonormée pour l'écran
		D3DXVECTOR3 vr; D3DXVECTOR3 nvr;
		D3DXVECTOR3 vu; D3DXVECTOR3 nvu;
		D3DXVECTOR3 vn; D3DXVECTOR3 nvn;
 
		D3DXVECTOR3 va;
		D3DXVECTOR3 vb;
		D3DXVECTOR3 vc;
 
		D3DXVec3Subtract(&vr, &pb, &pa);
		D3DXVec3Subtract(&vu,&pc,&pa);
 
		D3DXVec3Normalize(&nvr,&vr);
		D3DXVec3Normalize(&nvu,&vu);		
		D3DXVec3Cross(&vn, &nvr, &nvu);
		D3DXVec3Normalize(&nvn, &vn);
 
		//Détermine les vecteurs des coins de l'écran
		D3DXVec3Subtract(&va, &pa, &pe);
		D3DXVec3Subtract(&vb,&pb,&pe);
		D3DXVec3Subtract(&vc, &pc, &pe);
 
		//Distance yeux/plan de l'écran
		float d = - D3DXVec3Dot(&va,&vn);
 
		//Plan near, plan far
		float n = 1.0f, f = 20000.0f;
 
		//Extrémités du frustum de vue
		float l = D3DXVec3Dot(&nvr,&va) * n / d;
		float r = D3DXVec3Dot(&nvr,&vb) * n / d;
		float b = D3DXVec3Dot(&nvu,&va) * n / d;
		float t = D3DXVec3Dot(&nvu,&vc) * n / d;
 
		//D3DXMatrixPerspectiveOffCenterLH(&matProjection, l, r, b, t, n, f);
//équivalent de glFrustum
		myFrustum(&matProjection, l, r, b, t, n, f);
 
		d3ddev->SetTransform(D3DTS_PROJECTION, &matProjection);
 
		//Rotation de la projection pour qu'elle soit non-perpendiculaire
		D3DXMATRIX M;
		M._11 = vr.x; M._21 = vr.y; M._31 = vr.z; 
		M._12 = vu.x; M._22 = vu.y; M._32 = vu.z;
		M._13 = vn.x; M._23 = vn.y; M._33 = vn.z;
		M._44 = 1.0f;
 
		d3ddev->MultiplyTransform(D3DTS_PROJECTION, &M);
		D3DXMATRIX eyeTranslation;
		D3DXMatrixTranslation(&eyeTranslation, -pe.x, -pe.y, -pe.z);
		d3ddev->MultiplyTransform(D3DTS_PROJECTION, &eyeTranslation);
Bartimeus est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 27/07/2011, 12h00   #2
Membre Expert
 
Inscription : février 2006
Messages : 1 394
Détails du profil
Informations forums :
Inscription : février 2006
Messages : 1 394
Points : 2 070
Points : 2 070
je dirai que si tu mets la matrice view à l'identité et que rien ne marche, il doit y avoir un soucis dans le calcul de la matrice proj et/ou world, les 2 qui restent en gros.

ps: peut être un problème de transposition, vu la différence entre matrice ligne et matrice colonne de dx et d'opengl.
stardeath est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 27/07/2011, 12h07   #3
Invité régulier
 
Inscription : septembre 2007
Messages : 20
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 20
Points : 6
Points : 6
Mmm, pourtant j'ai fait un test en désactivant mon calcul spécial et en recalculant la matrice de projection normalement (avec la fonction DirectX qui va bien et qui fonctionnait avant que je tente d'implémenter la nouvelle méthode) tout en gardant une matrice de vue à l'identité et là non plus je ne voyais rien.

Ce qui est assez étrange car d'après ce que je lis sur le sujet la matrice de vue n'est pas forcément si importante que cela, elle n'applique que des rotations/translations pour déplacer la caméra (ou plutôt l'univers 3D mais c'est le principe).

Je vais continuer à regarder s'il n'y a pas une erreur dans mon calcul jusqu'à maintenant je n'ai rien trouvé de concluant...

A tout hasard : les matrices une dimensions à 16 valeurs dans OpenGL c'est bien l'équivalent d'une D3DXMATRIX à deux dimensions avec D3DXMATRIX(2,1) = OpenGLmatrix[4] ?

Edit : j'ai cru lire que les matrices directx étaient la transposée des matrices OpenGL. J'ai fait un test en utilisant D3DXMatrixTranspose à mes matrices initiales mais cela ne change rien (ou du moins j'ai toujours un écran vide).
Bartimeus est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 27/07/2011, 12h27   #4
Membre Expert
 
Inscription : février 2006
Messages : 1 394
Détails du profil
Informations forums :
Inscription : février 2006
Messages : 1 394
Points : 2 070
Points : 2 070
heu, si en utilisant les fonctions dx tu ne vois rien, ce n'est peut être pas du coté des matrices que se situe le problème. (genre, est ce que tes objets sont bien placés du fait du changement de repère entre opengl et dx, etc.)

concernant l'utilité de la matrice de vue, c'est une matrice, tout comme en opengl, tu pourrais tout faire avec la matrice proj mais ça serait chiant, en dx, tu as une matrice pour tes objets, une pour la caméra, et une pour la projection.
stardeath est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 27/07/2011, 12h33   #5
Invité régulier
 
Inscription : septembre 2007
Messages : 20
Détails du profil
Informations forums :
Inscription : septembre 2007
Messages : 20
Points : 6
Points : 6
Je vois mes objets quand j'utilise la méthode normale (matrice de vue initialisée avec D3DXMatrixLookAt et matrice de projection initialisée avec D3DXMatrixPerspectiveFovLH), par contre si je met la matrice de vue à l'identitée (de base je mettais la caméra à -50) je ne vois plus rien.

Bon en soit ça me paraît normal, je suppose que matrice de vue à l'identité correspond à une caméra en 0,0,0. Par contre dès que je tente ma méthode ça ne marche plus, avec ou sans matrice de vue. J'ai du mal à comprendre d'où pourrait venir le problème (ou tout simplement DirectX ne supporte pas les frustum off-axis, mais ça m'étonnerait).
Bartimeus est déconnecté   Envoyer un message privé Réponse avec citation 00
Vieux 02/08/2011, 01h10   #6
Membre Expert
 
Homme Eric Dureuil
Développeur informatique
Inscription : avril 2011
Messages : 865
Détails du profil
Informations personnelles :
Nom : Homme Eric Dureuil
Localisation : France, Isère (Rhône Alpes)

Informations professionnelles :
Activité : Développeur informatique
Secteur : High Tech - Multimédia et Internet

Informations forums :
Inscription : avril 2011
Messages : 865
Points : 1 348
Points : 1 348
salut,

que ce soit dans opengl ou dx, la matrice identité correspond à la caméra orienté le long de z, y vertical vers le haut et x horizontal orienté vers la droite...

c'est fait pour être directement compatible avec l'affichage 2d...

les matrices utilisées par les cartes graphiques sont toutes en notation anglo-saxonne (transposée de la notation française) attention pour les calculs donc au niveau des indices...

la différence entre matrices de positionnement/homothétie et celle de projection c'est que celle de projection va déterminer, souvent par rapport à l'ouverture, les plans de clipping... avec des formules qui tendent à faire sortir les points hors des limites de la zone de rendu s'ils sont au delà des plans de clipping... on a donc besoin d'une seul matrice de projection par scène... les matrices de positionnement/homothétie sont gérées sous forme d'une pile dont la taille peut être limité à 32 niveaux selon les systèmes

les cartes graphiques travaillent en coordonnées homogènes... ce qui explique qu'on utilise une matrice 4x4 pour décrire complétement un espace de dimension 3...

techniquement parlant, tu pourrais avoir comme matrice de projection 3 vecteurs de ton choix comme base de rendu pour réaliser une projection non classique, en les déterminant en fonction d'un point de fuite (technique de dessin) choisi...

les 2 systèmes sont donc directement transposables même si le passage de la matrice de projection n'est pas fait tout à fait de la même façon... les formules sont les mêmes
__________________
Eric Dureuil, développeur web, c/c++, java indépendant
soyons
pensez à mettre et
ericd69 est actuellement connecté   Envoyer un message privé Réponse avec citation 00
Réponse Proposer ce sujet en actualité
Outils de la discussion



Fuseau horaire GMT +2. Il est actuellement 15h11.


 
 
 
 
Partenaires

Hébergement Web