J’écris un petit utilitaire qui signale les capacités du système. L’un est le modèle de shader le plus élevé pris en charge par la carte graphique installée, et je le détecte actuellement en utilisant les capacités de l’appareil de Direct3D 9.0c et en vérifiant les champs VertexShaderVersion
et PixelShaderVersion
de la structure D3DCAPS9
.
HRESULT hrDCaps = poD3D9->GetDeviceCaps(D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, &oCaps); if (!FAILED(hrDCaps)) { // Pixel and vertex shader model versions. Use the minimum number of each for "the" shader model version const int iVertexShaderModel = D3DSHADER_VERSION_MAJOR(oCaps.VertexShaderVersion); const int iPixelShaderModel = D3DSHADER_VERSION_MAJOR(oCaps.PixelShaderVersion);
Cependant, ces deux valeurs renvoient le shader model 3 même pour les cartes prenant en charge des modèles plus élevés. Voici ce que GPU-Z renvoie pour la même carte, par exemple:
Cette question indique que DX9 ne rapportera jamais plus que SM3 même sur des cartes prenant en charge un modèle supérieur, mais ne mentionne pas comment le résoudre.
Comment obtenir avec précision le modèle de shader pris en charge par la carte installée? Autrement dit, les capacités de la carte, pas les capacités du pilote DirectX installé.
L’utilitaire doit fonctionner sous Windows 2000 et au-dessus, et fonctionner sur des systèmes où une carte graphique et même DirectX ne sont pas installés. Je charge actuellement dynamiquement DX9, donc sur ces systèmes, la vérification échoue gracieusement (ce qui est ok.) Mais je cherche une solution similaire: quelque chose qui fonctionnera toujours sur tous les systèmes et fonctionnera correctement (détecter la version SM) sur la plupart des systèmes.
Objectif d’édition: Je n’utilise pas ce code pour modifier dynamiquement les fonctionnalités d’un programme, c’est-à-dire sélectionner des shaders. Je l’utilise pour signaler les capacités matérielles comme un « ping » à un serveur, ce qui nous permet d’avoir une bonne idée du matériel typique que nos clients utilisent, ce qui peut éclairer les décisions futures sur les produits. (Exemple: combien de clients ont SM4 ou plus? Combien utilisent un système d’exploitation 64 bits? Etc.) C’est pourquoi (a) l’échec gracieux, donc nous savons qu’il a échoué, ou (b) l’obtention d’un numéro de modèle de shader précis sont les deux modes préférés.
Edit-answers jusqu’à présent: La réponse ci-dessous de SigTerm suggère d’instancier DirectX 11, 10.1, 10 et 9.0c dans l’ordre, et de baser le modèle de shader signalé sur lequel la version s’est instanciée sans échec (modèle de shader 5, 4.1, 4 et DXCAPS dans cet ordre.) Si possible, j’apprécierais un exemple de code du DX11 et 10 façons de le faire.
Ce n’est peut-être pas une solution fiable. Par exemple, j’exécute Windows sur une machine virtuelle VMware Fusion sous OSX. Les pilotes Fusion signalent DX11 dans DxDiag, mais je sais d’après les spécifications techniques de Fusion qu’il ne prend en charge que DX9.0c et shader model 3. Pourtant, à cette exception près, cette méthode semble le meilleur moyen jusqu’à présent.