Доступ к поплавкам оператора XMMatrix — () не работает

Я пытаюсь сделать некоторые 3D-вещи в DirectX (я мигрирую из OpenGL), и я столкнулся с проблемой.

Я хочу получить доступ к значениям XMMATRIX и, глядя на документацию Microsoft, должен быть оператор ():

    float&  operator ()(
size_t Row,
size_t Column
);

Поэтому я попытался использовать как таковой:

XMMATRIX i = XMMatrixIdentity();
float j = i(0,0);

Но Intellisense дает мне ошибку:

IntelliSense: вызов объекта типа класса без соответствующего оператора () или функций преобразования в указатель на тип функции.

Если я игнорирую Intellisense и все равно компилирую, я получаю ошибку времени компиляции:

ошибка C2064: термин не оценивает функцию, принимающую 2 аргумента

Кто-нибудь имеет представление о том, почему это происходит? Или другой способ доступа к элементам Матрицы?

Спасибо за ваше время.

Постскриптум Я создаю C ++ / DirectX Modern UI App для Windows 8, если эта информация поможет вообще.

2

Решение

Проверьте эта ссылка MSDN и вы увидите, что это зависит от того, какой математический заголовок DirectX или XNA у вас есть, и определения препроцессора, действовавшие в то время. По умолчанию и по причинам оптимизации матрицы и векторные структуры будут реализованы с использованием SSE и встроенных функций, что затрудняет и удорожает доступ к строкам / столбцам.

Попробуйте определить _XM_NO_INTRINSICS_ в директиве препроцессора записи C ++ свойств вашего проекта, или #define _XM_NO_INTRINSICS_ до тебя #include любые заголовки DirectX.

Этот отрывок из DirectXMath.h на моей системе Windows 8 VS2012 показывает, почему вы получаете эту ошибку:

struct XMMATRIX
{
// ... code removed for clarity

#ifdef _XM_NO_INTRINSICS_
float       operator() (size_t Row, size_t Column) const { return m[Row][Column]; }
float&      operator() (size_t Row, size_t Column) { return m[Row][Column]; }
#endif

// ... code removed for clarity
};
4

Другие решения

Индивидуальный элемент доступа для XMVECTOR а также XMMATRIX очень неэффективен из-за базового набора инструкций SIMD, поэтому библиотека DirectXMath не поддерживает его через методы-члены. Есть несколько способов добиться этого в зависимости от ваших потребностей.

Если вам просто нужен элемент (0,0), вы можете использовать:

float j = XMVectorGetX( i.r[0] );

Если вы собираетесь получить доступ к большинству или всем отдельным элементам XMMATRIX, лучшим решением будет выгрузить его в XMFLOAT4X4:

XMFLOAT4X4 tmp;
XMStoreFloat4x4( &tmp, i );
float j = tmp.m[0][0]; // or float j = tmp._11

Я отправлю сообщение об ошибке, потому что оператор (), упомянутый в MSDN, на самом деле является «XNAMath», а не «DirectXMath». Увидеть этот блог для некоторого фона.

Если вы находите DirectXMath слишком сложным для ваших нужд, вы можете рассмотреть возможность использования SimpleMath в Набор инструментов DirectX.

1

Я обнаружил, что это работает, я также основал свой код на том же учебнике по отбору лучей и перехожу с xnamath на directxmath.

Это выберет правильные значения из матрицы без необходимости отключения SSE Intrinsics.

«Проекция» — это XMMATRIX, содержащий матрицу вида с камеры.

    XMVECTOR xv = projection.r[0];
XMVECTOR yv = projection.r[1];
PRVecX =  ((( 2.0f * mouseX) / Window::ClientWidth) - 1 ) / XMVectorGetX(xv);
PRVecY = -((( 2.0f * mouseY) / Window::ClientHeight) - 1 ) / XMVectorGetY(yv);

Отключение встроенных функций с помощью плохой идея, потому что это сильно замедляет вашу программу. По возможности конвертируйте ваш код, чтобы правильно загружать и хранить внутренние значения, как указано выше.

1

Добавьте #define _XM_NO_INTRINSICS_ в начало файла。

#include <windows.h>
#define _XM_NO_INTRINSICS_//must before #include <DirectXMath.h>
#include <DirectXMath.h>
#include <iostream>
1

Ты можешь попробовать:

XMMATRIX i = XMMatrixIdentity();
float j = i.r[0].m128_f32[0];
0
По вопросам рекламы [email protected]