mirror of
https://github.com/Team-Resurgent/GamepadTest.git
synced 2026-04-30 10:36:37 -07:00
1154 lines
52 KiB
C++
1154 lines
52 KiB
C++
//-----------------------------------------------------------------------------
|
|
// File: Gamepad.cpp
|
|
//
|
|
// Desc: Tool to experiment with all things related to an Xbox gamepad
|
|
// controller
|
|
//
|
|
// Hist: 04.06.01 - Created
|
|
// 10.03.01 - Ensure use of only one gamepad
|
|
// 10.03.01 - Added count to quantization page
|
|
//
|
|
// Copyright (c) Microsoft Corporation. All rights reserved.
|
|
//-----------------------------------------------------------------------------
|
|
#include "Common\XBApp.h"
|
|
#include "Common\XBFont.h"
|
|
#include "Common\XBMesh.h"
|
|
#include "Common\XBUtil.h"
|
|
#include "Common\XBResource.h"
|
|
#include <xgraphics.h>
|
|
#include "Resource.h"
|
|
|
|
|
|
// Subsets for within the gamepad mesh. This are specific to the gamepad mesh.
|
|
// For instance, subset 7 represents an internal XBMESH_SUBSET structure for
|
|
// rendering the geometry for the gamepad's x button.
|
|
#define CONTROL_LEFTTHUMBSTICK 0
|
|
#define CONTROL_RIGHTTHUMBSTICK 1
|
|
#define CONTROL_BODY 2
|
|
#define CONTROL_BACKBUTTON 3
|
|
#define CONTROL_STARTBUTTON 4
|
|
#define CONTROL_ABUTTON 5
|
|
#define CONTROL_BBUTTON 6
|
|
#define CONTROL_XBUTTON 7
|
|
#define CONTROL_YBUTTON 8
|
|
#define CONTROL_WHITEBUTTON 9
|
|
#define CONTROL_BLACKBUTTON 10
|
|
#define CONTROL_CORDSTUB 11
|
|
#define CONTROL_GASKETS 12
|
|
#define CONTROL_MEMCARDSLOT 13
|
|
#define CONTROL_LEFTTRIGGER 14
|
|
#define CONTROL_RIGHTTRIGGER 15
|
|
#define CONTROL_DPAD 16
|
|
#define CONTROL_JEWEL 17
|
|
#define NUM_CONTROLS 18
|
|
|
|
|
|
// Offsets for building matrices which are used to animate the gamepad controls.
|
|
D3DXVECTOR3 g_vLeftTriggerAxis = D3DXVECTOR3( 1.0f, -0.13f, 0.0f );
|
|
D3DXVECTOR3 g_vLeftTriggerOffset = D3DXVECTOR3( 0.0f, 12.0f, 38.0f );
|
|
D3DXVECTOR3 g_vRightTriggerAxis = D3DXVECTOR3( 1.0f, 0.13f, 0.0f );
|
|
D3DXVECTOR3 g_vRightTriggerOffset = D3DXVECTOR3( 0.0f, 12.0f, 38.0f );
|
|
D3DXVECTOR3 g_vDPadOffset = D3DXVECTOR3( -36.70f, -26.27f, 12.0f );
|
|
D3DXVECTOR3 g_vLeftStickOffset = D3DXVECTOR3( -48.54f, 8.72f, 18.0f );
|
|
D3DXVECTOR3 g_vRightStickOffset = D3DXVECTOR3( 36.70f, -26.27f, 18.0f );
|
|
|
|
|
|
// Structures for animating, highlighting, and textureing the gamepad controls.
|
|
BOOL g_ControlActive[NUM_CONTROLS];
|
|
D3DXMATRIX g_ControlMatrix[NUM_CONTROLS];
|
|
LPDIRECT3DTEXTURE8 g_ControlTexture[NUM_CONTROLS];
|
|
|
|
|
|
// Global world matrix, so the app can orient the gamepad
|
|
D3DXMATRIX g_matWorld( 1,0,0,0, 0,1,0,0, 0,0,1,0, 0,0,0,1 );
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: class CGamepadMesh
|
|
// Desc: The gamepad mesh. This is overrided from the base class so that we can
|
|
// provide a custom RenderCallback() function.
|
|
//-----------------------------------------------------------------------------
|
|
class CGamepadMesh : public CXBMesh
|
|
{
|
|
public:
|
|
BOOL RenderCallback( LPDIRECT3DDEVICE8 pd3dDevice, DWORD dwSubset,
|
|
XBMESH_SUBSET* pSubset, DWORD dwFlags );
|
|
};
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: RenderCallback()
|
|
// Desc: Overrided from the base class so that we can animate and highlight
|
|
// individual mesh subsets before rendering them.
|
|
//-----------------------------------------------------------------------------
|
|
BOOL CGamepadMesh::RenderCallback( LPDIRECT3DDEVICE8 pd3dDevice, DWORD dwSubset,
|
|
XBMESH_SUBSET* pSubset, DWORD dwFlags )
|
|
{
|
|
// Set matrix
|
|
D3DXMATRIX mat = g_matWorld;
|
|
D3DXMatrixMultiply( &mat, &g_ControlMatrix[dwSubset], &mat );
|
|
pd3dDevice->SetTransform( D3DTS_WORLD, &mat );
|
|
|
|
// Set material
|
|
D3DMATERIAL8 mtrl;
|
|
XBUtil_InitMaterial( mtrl, 1.0f, 1.0f, 1.0f, 1.0f );
|
|
pd3dDevice->SetMaterial( &mtrl );
|
|
|
|
// Set texture
|
|
pd3dDevice->SetTexture( 0, g_ControlTexture[dwSubset] );
|
|
|
|
return TRUE;
|
|
};
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: class CXBoxSample
|
|
// Desc: Application class. The base class provides just about all the
|
|
// functionality we want, so we're just supplying stubs to interface with
|
|
// the non-C++ functions of the app.
|
|
//-----------------------------------------------------------------------------
|
|
class CXBoxSample : public CXBApplication
|
|
{
|
|
// Valid app states
|
|
enum APPSTATE
|
|
{
|
|
APPSTATE_CONTROLTEST=0,
|
|
APPSTATE_VIBRATIONTEST,
|
|
APPSTATE_DEADZONECALIBRATION,
|
|
APPSTATE_BUTTONQUANTIZATION,
|
|
APPSTATE_MEMORYUNITDETECTION,
|
|
APPSTATE_MAX,
|
|
};
|
|
|
|
// Valid gamepad types
|
|
enum GAMEPADTYPE
|
|
{
|
|
GAMEPADTYPE_NONE=0,
|
|
GAMEPADTYPE_US
|
|
};
|
|
|
|
// General application members
|
|
APPSTATE m_AppState; // State of the app
|
|
CXBPackedResource m_xprResource; // Packed resources for the app
|
|
CXBFont m_Font16; // 16-point font class
|
|
CXBFont m_Font12; // 12-point font class
|
|
|
|
// Active gamepad
|
|
DWORD m_dwNumInsertedGamepads;
|
|
XBGAMEPAD* m_pGamepad;
|
|
|
|
// Geometry
|
|
CGamepadMesh m_GamepadMesh; // Geometry for the US gamepad
|
|
CGamepadMesh m_GamepadSMesh; // Geometry for the Japan gamepad
|
|
CGamepadMesh* m_pGamepadMesh; // Geometry for the active gamepad
|
|
GAMEPADTYPE m_GamepadType; // Type of gamepad used
|
|
|
|
// Options
|
|
DWORD m_dwTextureSelection;
|
|
BOOL m_bAlphaEnabled;
|
|
|
|
// Vibration motor values
|
|
FLOAT m_fLeftMotorSpeed;
|
|
FLOAT m_fRightMotorSpeed;
|
|
|
|
// Deadzone calibration page
|
|
FLOAT m_fDeadZone;
|
|
|
|
// Control quantization page
|
|
BYTE* m_pQuantizedThumbStickValues;
|
|
BYTE* m_pQuantizedButtonValues;
|
|
|
|
// Internal members
|
|
VOID ShowTexture( LPDIRECT3DTEXTURE8 pTexture );
|
|
HRESULT DrawBox( FLOAT x1, FLOAT y1, FLOAT x2, FLOAT y2,
|
|
DWORD dwFillColor, DWORD dwOutlineColor );
|
|
HRESULT RenderInsertRemoveControllerPage();
|
|
HRESULT RenderControlTestPage();
|
|
HRESULT RenderVibrationTestPage();
|
|
HRESULT RenderDeadZoneCalibrationPage();
|
|
HRESULT RenderButtonQuantizationPage();
|
|
|
|
protected:
|
|
HRESULT Initialize();
|
|
HRESULT FrameMove();
|
|
HRESULT Render();
|
|
|
|
public:
|
|
CXBoxSample();
|
|
};
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: main()
|
|
// Desc: Entry point to the program.
|
|
//-----------------------------------------------------------------------------
|
|
VOID __cdecl main()
|
|
{
|
|
CXBoxSample xbApp;
|
|
if( FAILED( xbApp.Create() ) )
|
|
return;
|
|
xbApp.Run();
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: CXBoxSample()
|
|
// Desc: Application constructor. Sets attributes for the app.
|
|
//-----------------------------------------------------------------------------
|
|
CXBoxSample::CXBoxSample()
|
|
:CXBApplication()
|
|
{
|
|
// Override base class variable to enable fullscreen-antialiasing
|
|
m_d3dpp.MultiSampleType = D3DMULTISAMPLE_2_SAMPLES_MULTISAMPLE_LINEAR |
|
|
D3DMULTISAMPLE_PREFILTER_FORMAT_X8R8G8B8;
|
|
|
|
m_AppState = APPSTATE_CONTROLTEST;
|
|
m_dwNumInsertedGamepads = 0L;
|
|
m_pGamepad = &m_DefaultGamepad;
|
|
m_GamepadType = GAMEPADTYPE_NONE;
|
|
m_pGamepadMesh = NULL;
|
|
m_dwTextureSelection = 0L;
|
|
m_bAlphaEnabled = FALSE;
|
|
m_fDeadZone = 0.24f; // Set default deadzone to 24%
|
|
m_fLeftMotorSpeed = 0.0f;
|
|
m_fRightMotorSpeed = 0.0f;
|
|
|
|
// Quantized control values
|
|
m_pQuantizedThumbStickValues = new BYTE[256];
|
|
ZeroMemory( m_pQuantizedThumbStickValues, 256 );
|
|
|
|
m_pQuantizedButtonValues = new BYTE[256];
|
|
ZeroMemory( m_pQuantizedButtonValues, 256 );
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: Initialize()
|
|
// Desc: This creates all device-dependent display objects.
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::Initialize()
|
|
{
|
|
// Create the resources
|
|
if( FAILED( m_xprResource.Create( m_pd3dDevice, "Resource.xpr",
|
|
resource_NUM_RESOURCES ) ) )
|
|
return XBAPPERR_MEDIANOTFOUND;
|
|
|
|
// Create the fonts
|
|
if( FAILED( m_Font16.Create( m_pd3dDevice, "Font16.xpr" ) ) )
|
|
return XBAPPERR_MEDIANOTFOUND;
|
|
if( FAILED( m_Font12.Create( m_pd3dDevice, "Font12.xpr" ) ) )
|
|
return XBAPPERR_MEDIANOTFOUND;
|
|
|
|
// Load the gamepad objects
|
|
if( FAILED( m_GamepadMesh.Create( m_pd3dDevice, "Models\\Gamepad.xbg" ) ) )
|
|
return XBAPPERR_MEDIANOTFOUND;
|
|
|
|
// Initialize the control highlight states, matrices, and textures
|
|
for( DWORD i=0; i< NUM_CONTROLS; i++ )
|
|
{
|
|
g_ControlActive[i] = FALSE;
|
|
D3DXMatrixIdentity( &g_ControlMatrix[i] );
|
|
g_ControlTexture[i] = NULL;
|
|
}
|
|
|
|
g_ControlTexture[CONTROL_BODY] = m_xprResource.GetTexture( resource_MatteBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_GASKETS] = m_xprResource.GetTexture( resource_MatteBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_LEFTTHUMBSTICK] = m_xprResource.GetTexture( resource_MatteBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_RIGHTTHUMBSTICK] = m_xprResource.GetTexture( resource_MatteBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_JEWEL] = m_xprResource.GetTexture( resource_GreenBezel_OFFSET );
|
|
g_ControlTexture[CONTROL_CORDSTUB] = m_xprResource.GetTexture( resource_Cord_OFFSET );
|
|
|
|
g_ControlTexture[CONTROL_MEMCARDSLOT] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_BACKBUTTON] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_STARTBUTTON] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_LEFTTRIGGER] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_RIGHTTRIGGER] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_DPAD] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
g_ControlTexture[CONTROL_ABUTTON] = m_xprResource.GetTexture( resource_GreenGlass_OFFSET );
|
|
g_ControlTexture[CONTROL_BBUTTON] = m_xprResource.GetTexture( resource_RedGlass_OFFSET );
|
|
g_ControlTexture[CONTROL_XBUTTON] = m_xprResource.GetTexture( resource_BlueGlass_OFFSET );
|
|
g_ControlTexture[CONTROL_YBUTTON] = m_xprResource.GetTexture( resource_YellowGlass_OFFSET );
|
|
g_ControlTexture[CONTROL_WHITEBUTTON] = m_xprResource.GetTexture( resource_WhiteGlass_OFFSET );
|
|
g_ControlTexture[CONTROL_BLACKBUTTON] = m_xprResource.GetTexture( resource_ShinyBlack_OFFSET );
|
|
|
|
// Misc render states
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_MAGFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_MINFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_MAGFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_MINFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetRenderState( D3DRS_DITHERENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_SPECULARENABLE, FALSE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ZENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_AMBIENT, 0xffffffff );
|
|
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE );
|
|
|
|
// Set up world matrix
|
|
D3DXMATRIX matWorld;
|
|
D3DXMatrixIdentity( &matWorld );
|
|
m_pd3dDevice->SetTransform( D3DTS_WORLD, &matWorld );
|
|
|
|
// Set up view matrix
|
|
D3DXMATRIX matView;
|
|
D3DXVECTOR3 vEyePt = D3DXVECTOR3( 0.0f, 0.0f,-250.0f );
|
|
D3DXVECTOR3 vLookatPt = D3DXVECTOR3( 0.0f, 0.0f, 0.0f );
|
|
D3DXVECTOR3 vUpVec = D3DXVECTOR3( 0.0f, 1.0f, 0.0f );
|
|
D3DXMatrixLookAtLH( &matView, &vEyePt, &vLookatPt, &vUpVec );
|
|
m_pd3dDevice->SetTransform( D3DTS_VIEW, &matView );
|
|
|
|
// Set up proj matrix
|
|
D3DXMATRIX matProj;
|
|
D3DXMatrixPerspectiveFovLH( &matProj, D3DX_PI/4, 4.0f/3.0f, 1.0f, 1000.0f );
|
|
m_pd3dDevice->SetTransform( D3DTS_PROJECTION, &matProj );
|
|
|
|
// Setup a base material
|
|
D3DMATERIAL8 mtrl;
|
|
XBUtil_InitMaterial( mtrl, 1.0f, 1.0f, 1.0f, 1.0f );
|
|
m_pd3dDevice->SetMaterial( &mtrl );
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: FrameMove()
|
|
// Desc: Called once per frame, the call is the entry point for animating
|
|
// the scene.
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::FrameMove()
|
|
{
|
|
// Detect the number and type of gamepads that are inserted. By default,
|
|
// use the US gamepad (aka "Xbox Controller"), unless any gamepad slot has
|
|
// a Japan gamepad (aka "Xbox Controller S") plugged into it. For this
|
|
// sample, we do this every frame just in case someone puts in a different
|
|
// controller.
|
|
m_dwNumInsertedGamepads = 0;
|
|
m_GamepadType = GAMEPADTYPE_NONE;
|
|
for( DWORD i=0; i<4; i++ )
|
|
{
|
|
if( m_Gamepad[i].hDevice )
|
|
{
|
|
// For all other controller types, use the US controller
|
|
m_pGamepad = &m_Gamepad[i];
|
|
m_GamepadType = GAMEPADTYPE_US;
|
|
m_dwNumInsertedGamepads++;
|
|
}
|
|
}
|
|
if( GAMEPADTYPE_US == m_GamepadType )
|
|
{
|
|
m_pGamepadMesh = &m_GamepadMesh;
|
|
g_vLeftTriggerAxis = D3DXVECTOR3( 1.00f, -0.13f, 0.0f );
|
|
g_vLeftTriggerOffset = D3DXVECTOR3( 0.00f, 12.00f, 38.0f );
|
|
g_vRightTriggerAxis = D3DXVECTOR3( 1.00f, 0.13f, 0.0f );
|
|
g_vRightTriggerOffset = D3DXVECTOR3( 0.00f, 12.00f, 38.0f );
|
|
g_vDPadOffset = D3DXVECTOR3(-36.70f,-26.27f, 12.0f );
|
|
g_vLeftStickOffset = D3DXVECTOR3(-48.54f, 8.72f, 18.0f );
|
|
g_vRightStickOffset = D3DXVECTOR3( 36.70f,-26.27f, 18.0f );
|
|
}
|
|
else
|
|
m_pGamepadMesh = NULL;
|
|
|
|
// Move to next app state when user presses BACK and START together
|
|
BOOL bStartAndBackButtonsPushed = FALSE;
|
|
|
|
if( ( m_pGamepad->wButtons & XINPUT_GAMEPAD_START ) &&
|
|
( m_pGamepad->wPressedButtons & XINPUT_GAMEPAD_BACK ) )
|
|
bStartAndBackButtonsPushed = TRUE;
|
|
|
|
if( ( m_pGamepad->wButtons & XINPUT_GAMEPAD_BACK ) &&
|
|
( m_pGamepad->wPressedButtons & XINPUT_GAMEPAD_START ) )
|
|
bStartAndBackButtonsPushed = TRUE;
|
|
|
|
if( bStartAndBackButtonsPushed )
|
|
{
|
|
switch( m_AppState )
|
|
{
|
|
case APPSTATE_CONTROLTEST: m_AppState = APPSTATE_VIBRATIONTEST; break;
|
|
case APPSTATE_VIBRATIONTEST: m_AppState = APPSTATE_DEADZONECALIBRATION; break;
|
|
case APPSTATE_DEADZONECALIBRATION: m_AppState = APPSTATE_BUTTONQUANTIZATION; break;
|
|
case APPSTATE_BUTTONQUANTIZATION: m_AppState = APPSTATE_CONTROLTEST; break;
|
|
}
|
|
|
|
m_fLeftMotorSpeed = 0.0f;
|
|
m_fRightMotorSpeed = 0.0f;
|
|
}
|
|
|
|
// Handle the control test page
|
|
if( m_AppState == APPSTATE_CONTROLTEST )
|
|
{
|
|
// Select options
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_START )
|
|
{
|
|
if( m_pGamepad->bPressedAnalogButtons[XINPUT_GAMEPAD_X] )
|
|
{
|
|
static dwTexture = 0;
|
|
dwTexture = (dwTexture+1)%resource_NUM_RESOURCES;
|
|
g_ControlTexture[CONTROL_BODY] = m_xprResource.GetTexture( 20L*dwTexture );
|
|
}
|
|
|
|
if( m_pGamepad->bPressedAnalogButtons[XINPUT_GAMEPAD_Y] )
|
|
{
|
|
static dwTexture = 0;
|
|
dwTexture = (dwTexture+1)%resource_NUM_RESOURCES;
|
|
g_ControlTexture[ CONTROL_LEFTTHUMBSTICK ] = m_xprResource.GetTexture( 20L*dwTexture );
|
|
g_ControlTexture[ CONTROL_RIGHTTHUMBSTICK ] = m_xprResource.GetTexture( 20L*dwTexture );
|
|
}
|
|
|
|
if( m_pGamepad->bPressedAnalogButtons[XINPUT_GAMEPAD_A] )
|
|
m_bAlphaEnabled = !m_bAlphaEnabled;
|
|
}
|
|
|
|
// Perform object rotation
|
|
D3DXMATRIX matRotate;
|
|
FLOAT fXRotate = m_pGamepad->fX1*m_fElapsedTime*D3DX_PI*0.5f;
|
|
FLOAT fYRotate = m_pGamepad->fY1*m_fElapsedTime*D3DX_PI*0.5f;
|
|
D3DXMatrixRotationYawPitchRoll( &matRotate, -fXRotate, -fYRotate, 0.0f );
|
|
D3DXMatrixMultiply( &g_matWorld, &g_matWorld, &matRotate );
|
|
m_pd3dDevice->SetTransform( D3DTS_WORLD, &g_matWorld );
|
|
|
|
// Record which controls are active
|
|
g_ControlActive[CONTROL_LEFTTHUMBSTICK] = ( m_pGamepad->wButtons & XINPUT_GAMEPAD_LEFT_THUMB ||
|
|
m_pGamepad->fX1 || m_pGamepad->fY1 ) ? TRUE : FALSE;
|
|
g_ControlActive[CONTROL_RIGHTTHUMBSTICK] = ( m_pGamepad->wButtons & XINPUT_GAMEPAD_RIGHT_THUMB ||
|
|
m_pGamepad->fX2 || m_pGamepad->fY2 ) ? TRUE : FALSE;
|
|
g_ControlActive[CONTROL_BACKBUTTON] = ( m_pGamepad->wButtons & XINPUT_GAMEPAD_BACK ) ? TRUE : FALSE;
|
|
g_ControlActive[CONTROL_STARTBUTTON] = ( m_pGamepad->wButtons & XINPUT_GAMEPAD_START ) ? TRUE : FALSE;
|
|
g_ControlActive[CONTROL_DPAD] = ( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_UP ||
|
|
m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_DOWN ||
|
|
m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_LEFT ||
|
|
m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_RIGHT ) ? TRUE : FALSE;
|
|
g_ControlActive[CONTROL_ABUTTON] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_A];
|
|
g_ControlActive[CONTROL_BBUTTON] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_B];
|
|
g_ControlActive[CONTROL_XBUTTON] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_X];
|
|
g_ControlActive[CONTROL_YBUTTON] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_Y];
|
|
g_ControlActive[CONTROL_BLACKBUTTON] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_BLACK];
|
|
g_ControlActive[CONTROL_WHITEBUTTON] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_WHITE];
|
|
g_ControlActive[CONTROL_LEFTTRIGGER] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_LEFT_TRIGGER];
|
|
g_ControlActive[CONTROL_RIGHTTRIGGER] = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_RIGHT_TRIGGER];
|
|
|
|
|
|
// Animate buttons
|
|
{
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_LEFTTHUMBSTICK], 0.0f, 0.0f, m_pGamepad->wButtons & XINPUT_GAMEPAD_LEFT_THUMB ? 1.0f : 0.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_RIGHTTHUMBSTICK], 0.0f, 0.0f, m_pGamepad->wButtons & XINPUT_GAMEPAD_RIGHT_THUMB ? 1.0f : 0.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_BACKBUTTON], 0.0f, 0.0f, m_pGamepad->wButtons & XINPUT_GAMEPAD_BACK ? 1.5f : 0.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_STARTBUTTON], 0.0f, 0.0f, m_pGamepad->wButtons & XINPUT_GAMEPAD_START ? 1.5f : 0.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_ABUTTON], 0.0f, 0.0f, 2.0f * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_A] / 255.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_BBUTTON], 0.0f, 0.0f, 2.0f * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_B] / 255.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_XBUTTON], 0.0f, 0.0f, 2.0f * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_X] / 255.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_YBUTTON], 0.0f, 0.0f, 2.0f * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_Y] / 255.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_BLACKBUTTON], 0.0f, 0.0f, 2.0f * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_BLACK] / 255.0f );
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_WHITEBUTTON], 0.0f, 0.0f, 2.0f * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_WHITE] / 255.0f );
|
|
}
|
|
|
|
// Animate left trigger
|
|
{
|
|
D3DXMATRIX matTrans1, matRotate, matTrans2, matAll;
|
|
D3DXMatrixTranslation( &matTrans1, -g_vLeftTriggerOffset.x, -g_vLeftTriggerOffset.y, -g_vLeftTriggerOffset.z );
|
|
D3DXMatrixRotationAxis( &matRotate, &g_vLeftTriggerAxis, (D3DX_PI/6) * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_LEFT_TRIGGER] / 255.0f );
|
|
D3DXMatrixTranslation( &matTrans2, g_vLeftTriggerOffset.x, g_vLeftTriggerOffset.y, g_vLeftTriggerOffset.z );
|
|
D3DXMatrixMultiply( &matAll, &matTrans1, &matRotate );
|
|
D3DXMatrixMultiply( &matAll, &matAll, &matTrans2 );
|
|
g_ControlMatrix[CONTROL_LEFTTRIGGER] = matAll;
|
|
}
|
|
|
|
// Animate right trigger
|
|
{
|
|
D3DXMATRIX matTrans1, matRotate, matTrans2, matAll;
|
|
D3DXMatrixTranslation( &matTrans1, -g_vRightTriggerOffset.x, -g_vRightTriggerOffset.y, -g_vRightTriggerOffset.z );
|
|
D3DXMatrixRotationAxis( &matRotate, &g_vRightTriggerAxis, (D3DX_PI/6) * m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_RIGHT_TRIGGER] / 255.0f );
|
|
D3DXMatrixTranslation( &matTrans2, g_vRightTriggerOffset.x, g_vRightTriggerOffset.y, g_vRightTriggerOffset.z );
|
|
D3DXMatrixMultiply( &matAll, &matTrans1, &matRotate );
|
|
D3DXMatrixMultiply( &matAll, &matAll, &matTrans2 );
|
|
g_ControlMatrix[CONTROL_RIGHTTRIGGER] = matAll;
|
|
}
|
|
|
|
// Animate DPAD
|
|
{
|
|
D3DXVECTOR3 vAxis(0,0,0);
|
|
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_UP ) vAxis.x = +1.0f;
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_DOWN ) vAxis.x = -1.0f;
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_LEFT ) vAxis.y = +1.0f;
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_RIGHT ) vAxis.y = -1.0f;
|
|
|
|
if( vAxis.x || vAxis.y )
|
|
{
|
|
D3DXMATRIX matTrans1, matRotate, matTrans2, matAll;
|
|
D3DXMatrixTranslation( &matTrans1, -g_vDPadOffset.x, -g_vDPadOffset.y, -g_vDPadOffset.z );
|
|
D3DXMatrixRotationAxis( &matRotate, &vAxis, D3DX_PI/20 );
|
|
D3DXMatrixTranslation( &matTrans2, g_vDPadOffset.x, g_vDPadOffset.y, g_vDPadOffset.z );
|
|
D3DXMatrixMultiply( &matAll, &matTrans1, &matRotate );
|
|
D3DXMatrixMultiply( &matAll, &matAll, &matTrans2 );
|
|
g_ControlMatrix[CONTROL_DPAD] = matAll;
|
|
}
|
|
else
|
|
D3DXMatrixIdentity( &g_ControlMatrix[CONTROL_DPAD] );
|
|
}
|
|
|
|
// Animate left thumbstick
|
|
{
|
|
D3DXVECTOR3 vAxis(0,0,0);
|
|
|
|
vAxis.x = +m_pGamepad->fY1;
|
|
vAxis.y = -m_pGamepad->fX1;
|
|
|
|
FLOAT fStickTrans = m_pGamepad->wButtons & XINPUT_GAMEPAD_LEFT_THUMB ? 1.0f : 0.0f;
|
|
|
|
if( vAxis.x || vAxis.y )
|
|
{
|
|
D3DXMATRIX matTrans1, matRotate, matTrans2, matAll;
|
|
D3DXMatrixTranslation( &matTrans1, -g_vLeftStickOffset.x, -g_vLeftStickOffset.y, -g_vLeftStickOffset.z );
|
|
D3DXMatrixRotationAxis( &matRotate, &vAxis, D3DXVec3Length( &vAxis)/3 );
|
|
D3DXMatrixTranslation( &matTrans2, g_vLeftStickOffset.x, g_vLeftStickOffset.y, g_vLeftStickOffset.z+fStickTrans );
|
|
D3DXMatrixMultiply( &matAll, &matTrans1, &matRotate );
|
|
D3DXMatrixMultiply( &matAll, &matAll, &matTrans2 );
|
|
g_ControlMatrix[CONTROL_LEFTTHUMBSTICK] = matAll;
|
|
}
|
|
else
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_LEFTTHUMBSTICK], 0.0f, 0.0f, fStickTrans );
|
|
}
|
|
|
|
// Animate right thumbstick
|
|
{
|
|
D3DXVECTOR3 vAxis(0,0,0);
|
|
|
|
vAxis.x = +m_pGamepad->fY2;
|
|
vAxis.y = -m_pGamepad->fX2;
|
|
|
|
FLOAT fStickTrans = m_pGamepad->wButtons & XINPUT_GAMEPAD_RIGHT_THUMB ? 1.0f : 0.0f;
|
|
|
|
if( vAxis.x || vAxis.y )
|
|
{
|
|
D3DXMATRIX matTrans1, matRotate, matTrans2, matAll;
|
|
D3DXMatrixTranslation( &matTrans1, -g_vRightStickOffset.x, -g_vRightStickOffset.y, -g_vRightStickOffset.z );
|
|
D3DXMatrixRotationAxis( &matRotate, &vAxis, D3DXVec3Length( &vAxis)/3 );
|
|
D3DXMatrixTranslation( &matTrans2, g_vRightStickOffset.x, g_vRightStickOffset.y, g_vRightStickOffset.z+fStickTrans );
|
|
D3DXMatrixMultiply( &matAll, &matTrans1, &matRotate );
|
|
D3DXMatrixMultiply( &matAll, &matAll, &matTrans2 );
|
|
g_ControlMatrix[CONTROL_RIGHTTHUMBSTICK] = matAll;
|
|
}
|
|
else
|
|
D3DXMatrixTranslation( &g_ControlMatrix[CONTROL_RIGHTTHUMBSTICK], 0.0f, 0.0f, fStickTrans );
|
|
}
|
|
}
|
|
|
|
// Handle the vibration test page
|
|
if( m_AppState == APPSTATE_VIBRATIONTEST )
|
|
{
|
|
m_fLeftMotorSpeed = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_LEFT_TRIGGER] / 255.0f;
|
|
m_fRightMotorSpeed = m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_RIGHT_TRIGGER] / 255.0f;
|
|
}
|
|
|
|
// Handle the deadzone calibration page
|
|
if( m_AppState == APPSTATE_DEADZONECALIBRATION )
|
|
{
|
|
// Adjust the deadzone
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_UP )
|
|
m_fDeadZone += 1.0f/256.0f;
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_DOWN )
|
|
m_fDeadZone -= 1.0f/256.0f;
|
|
m_fDeadZone = min( 1.0f, max( 0.0f, m_fDeadZone ) );
|
|
}
|
|
|
|
// Handle the button quantization page
|
|
if( m_AppState == APPSTATE_BUTTONQUANTIZATION )
|
|
{
|
|
// Reset the recorded values
|
|
if( m_pGamepad->wButtons & XINPUT_GAMEPAD_START )
|
|
{
|
|
ZeroMemory( m_pQuantizedThumbStickValues, 256 );
|
|
ZeroMemory( m_pQuantizedButtonValues, 256 );
|
|
}
|
|
|
|
// Record quantized thumbstick values
|
|
m_pQuantizedThumbStickValues[ (32768 + m_pGamepad->sThumbLX) >> 8 ] |= 0x01;
|
|
m_pQuantizedThumbStickValues[ (32768 + m_pGamepad->sThumbLY) >> 8 ] |= 0x02;
|
|
m_pQuantizedThumbStickValues[ (32768 + m_pGamepad->sThumbRX) >> 8 ] |= 0x04;
|
|
m_pQuantizedThumbStickValues[ (32768 + m_pGamepad->sThumbRY) >> 8 ] |= 0x08;
|
|
|
|
// Record quantized button values
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[0] ] |= 0x01;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[1] ] |= 0x02;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[2] ] |= 0x04;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[3] ] |= 0x08;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[4] ] |= 0x10;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[5] ] |= 0x20;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[6] ] |= 0x40;
|
|
m_pQuantizedButtonValues[ m_pGamepad->bAnalogButtons[7] ] |= 0x80;
|
|
}
|
|
|
|
// Set the vibration motors
|
|
for( DWORD i=0; i<4; i++ )
|
|
{
|
|
if( m_Gamepad[i].hDevice )
|
|
{
|
|
// Check to see if we are still transferring current motor value
|
|
if( m_Gamepad[i].Feedback.Header.dwStatus != ERROR_IO_PENDING )
|
|
{
|
|
// We can alter the motor values
|
|
m_Gamepad[i].Feedback.Rumble.wLeftMotorSpeed = WORD( m_fLeftMotorSpeed * 65535.0f );
|
|
m_Gamepad[i].Feedback.Rumble.wRightMotorSpeed = WORD( m_fRightMotorSpeed * 65535.0f );
|
|
XInputSetState( m_Gamepad[i].hDevice, &m_Gamepad[i].Feedback );
|
|
}
|
|
}
|
|
}
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: DrawBox()
|
|
// Desc: Graphics helper function
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::DrawBox( FLOAT x1, FLOAT y1, FLOAT x2, FLOAT y2,
|
|
DWORD dwFillColor, DWORD dwOutlineColor )
|
|
{
|
|
D3DXVECTOR4 v[4];
|
|
v[0] = D3DXVECTOR4( x1-0.5f, y1-0.5f, 0, 0 );
|
|
v[1] = D3DXVECTOR4( x2-0.5f, y1-0.5f, 0, 0 );
|
|
v[2] = D3DXVECTOR4( x2-0.5f, y2-0.5f, 0, 0 );
|
|
v[3] = D3DXVECTOR4( x1-0.5f, y2-0.5f, 0, 0 );
|
|
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1 );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TFACTOR );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAARG1, D3DTA_TFACTOR );
|
|
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
|
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_SRCBLEND, D3DBLEND_SRCALPHA );
|
|
m_pd3dDevice->SetRenderState( D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA );
|
|
m_pd3dDevice->SetVertexShader( D3DFVF_XYZRHW );
|
|
|
|
// Render the box
|
|
m_pd3dDevice->SetRenderState( D3DRS_TEXTUREFACTOR, dwFillColor );
|
|
m_pd3dDevice->DrawVerticesUP( D3DPT_QUADLIST, 4, v, sizeof(v[0]) );
|
|
|
|
// Render the lines
|
|
m_pd3dDevice->SetRenderState( D3DRS_TEXTUREFACTOR, dwOutlineColor );
|
|
m_pd3dDevice->DrawVerticesUP( D3DPT_LINELOOP, 4, v, sizeof(v[0]) );
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: RenderInsertRemoveControllerPage()
|
|
// Desc: Inform the user to please insert or remove a controller
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::RenderInsertRemoveControllerPage()
|
|
{
|
|
// Draw a gradient filled background
|
|
RenderGradientBackground( 0xff0000ff, 0xff000000 );
|
|
|
|
// Set some default state
|
|
m_pd3dDevice->SetRenderState( D3DRS_MULTISAMPLEANTIALIAS, TRUE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_MAGFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_MINFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ZENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_AMBIENT, 0x00ffffff );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, FALSE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, TRUE );
|
|
|
|
// Draw header
|
|
DrawBox( 64, 50, 576, 93, 0x40000000, 0xff000000 );
|
|
m_Font16.DrawText( 69, 50, 0xffffffff, L"Xbox Controller Tool", XBFONT_LEFT );
|
|
|
|
// Display a message requesting the user to insert a gamepad controller. Since
|
|
// the Xbox input API take a second or so to detect a controller, let's delay
|
|
// this message a tiny bit
|
|
if( m_fAppTime > 2.0f )
|
|
{
|
|
DrawBox( 64, 103, 576, 430, 0x40000000, 0xff000000 );
|
|
|
|
if( m_dwNumInsertedGamepads == 0 )
|
|
m_Font16.DrawText( 320, 250, 0xffffffff, L"Please insert a gamepad controller", XBFONT_CENTER_X );
|
|
else // if( m_dwNumInsertedGamepads > 1 )
|
|
m_Font16.DrawText( 320, 250, 0xffffffff, L"Please remove all but one gamepad controllers", XBFONT_CENTER_X );
|
|
}
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: RenderControlTestPage()
|
|
// Desc: Renders the page for testing the controls
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::RenderControlTestPage()
|
|
{
|
|
// Draw a gradient filled background
|
|
RenderGradientBackground( 0xff0000ff, 0xff000000 );
|
|
|
|
// Set some default state
|
|
m_pd3dDevice->SetRenderState( D3DRS_MULTISAMPLEANTIALIAS, TRUE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_MAGFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_MINFILTER, D3DTEXF_LINEAR );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ZENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_AMBIENT, 0x00ffffff );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, FALSE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, TRUE );
|
|
|
|
// Since xrays go through objects, it only looks convincing if we turn on
|
|
// alpha-blending and render both sides of the object
|
|
if( m_bAlphaEnabled )
|
|
{
|
|
// Lighting is not needed, since we don't use the diffuse color
|
|
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, FALSE );
|
|
|
|
// Setup to render both sides of the object
|
|
m_pd3dDevice->SetRenderState( D3DRS_ZWRITEENABLE, FALSE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE );
|
|
|
|
// Turn on alpha blending
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_SRCBLEND, D3DBLEND_SRCCOLOR );
|
|
m_pd3dDevice->SetRenderState( D3DRS_DESTBLEND, D3DBLEND_ONE );
|
|
|
|
// Set the transparency
|
|
m_pd3dDevice->SetRenderState( D3DRS_TEXTUREFACTOR, 0x80808080 );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG2, D3DTA_TFACTOR );
|
|
}
|
|
|
|
// Generate spheremap texture coords from the camera space normal. This has
|
|
// two steps. First, tell D3D to use the vertex normal (in camera space) as
|
|
// texture coordinates. Then, we setup a texture matrix to transform these
|
|
// texcoords from (-1,+1) view space to (0,1) texture space. This way,
|
|
// the normal can be used to look up a texel in the spheremap.
|
|
D3DXMATRIX mat;
|
|
mat._11 = 0.5f; mat._12 = 0.0f;
|
|
mat._21 = 0.0f; mat._22 =-0.5f;
|
|
mat._31 = 0.0f; mat._32 = 0.0f;
|
|
mat._41 = 0.5f; mat._42 = 0.5f;
|
|
m_pd3dDevice->SetTransform( D3DTS_TEXTURE0, &mat );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_COUNT2 );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_CAMERASPACENORMAL );
|
|
|
|
// Finally, draw the object
|
|
m_pGamepadMesh->Render( m_pd3dDevice, XBMESH_NOTEXTURES|XBMESH_NOMATERIALS );
|
|
|
|
// Restore render states
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_TEXTURETRANSFORMFLAGS, D3DTTFF_DISABLE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_TEXCOORDINDEX, D3DTSS_TCI_PASSTHRU );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, FALSE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ZWRITEENABLE, TRUE );
|
|
|
|
// Draw back side to fill holes
|
|
if( FALSE == m_bAlphaEnabled )
|
|
{
|
|
m_pd3dDevice->SetTexture( 0, NULL );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1 );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TFACTOR );
|
|
m_pd3dDevice->SetRenderState( D3DRS_TEXTUREFACTOR, 0xff000000 );
|
|
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, FALSE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_CW );
|
|
m_pGamepadMesh->Render( m_pd3dDevice, XBMESH_NOTEXTURES|XBMESH_NOMATERIALS );
|
|
}
|
|
|
|
// Restore render states
|
|
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_CCW );
|
|
m_pd3dDevice->SetRenderState( D3DRS_MULTISAMPLEANTIALIAS, FALSE );
|
|
|
|
|
|
// Draw header
|
|
DrawBox( 64, 50, 576, 93, 0x40000000, 0xff000000 );
|
|
m_Font16.DrawText( 69, 50, 0xffffffff, L"Xbox Controller Tool", XBFONT_LEFT );
|
|
m_Font16.DrawText( 571, 50, 0xffffffff, L"Control Test Page", XBFONT_RIGHT );
|
|
m_Font12.DrawText( 571, 75, 0xff808080, L"Press START and BACK for next page", XBFONT_RIGHT );
|
|
|
|
// Draw options
|
|
m_Font12.Begin();
|
|
|
|
|
|
WCHAR strBuffer[40];
|
|
|
|
swprintf( strBuffer, L"LeftTrigger = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_LEFT_TRIGGER] );
|
|
m_Font12.DrawText( 140, 95, m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_LEFT_TRIGGER] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
|
|
swprintf( strBuffer, L"RightTrigger = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_RIGHT_TRIGGER] );
|
|
m_Font12.DrawText( 350, 95, m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_RIGHT_TRIGGER] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
|
|
swprintf( strBuffer, L"LeftStick.x = %d", m_pGamepad->sThumbLX );
|
|
m_Font12.DrawText( 64, 116, m_pGamepad->fX1!=0.0f ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"LeftStick.y = %d", m_pGamepad->sThumbLY );
|
|
m_Font12.DrawText( 64, 134, m_pGamepad->fY1!=0.0f ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"LeftThumb" );
|
|
m_Font12.DrawText( 64, 152, m_pGamepad->wButtons & XINPUT_GAMEPAD_LEFT_THUMB ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
|
|
m_Font12.DrawText( 110, 362, m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_UP ? 0xffffff00: 0x80ffffff, L"Up", XBFONT_CENTER_X );
|
|
m_Font12.DrawText( 85, 380, m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_LEFT ? 0xffffff00: 0x80ffffff, L"Left", XBFONT_CENTER_X );
|
|
m_Font12.DrawText( 135, 380, m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_RIGHT ? 0xffffff00: 0x80ffffff, L"Right", XBFONT_CENTER_X );
|
|
m_Font12.DrawText( 110, 398, m_pGamepad->wButtons & XINPUT_GAMEPAD_DPAD_DOWN ? 0xffffff00: 0x80ffffff, L"Down", XBFONT_CENTER_X );
|
|
|
|
m_Font12.DrawText( 320, 380, g_ControlActive[CONTROL_BACKBUTTON] ? 0xffffff00: 0x80ffffff, L"Back", XBFONT_RIGHT );
|
|
m_Font12.DrawText( 330, 380, g_ControlActive[CONTROL_STARTBUTTON] ? 0xffffff00: 0x80ffffff, L"Start", XBFONT_LEFT );
|
|
|
|
swprintf( strBuffer, L"White = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_WHITE] );
|
|
m_Font12.DrawText( 390, 116, g_ControlActive[CONTROL_WHITEBUTTON] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"Y = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_Y] );
|
|
m_Font12.DrawText( 390, 134, g_ControlActive[CONTROL_YBUTTON] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"X = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_X] );
|
|
m_Font12.DrawText( 390, 152, g_ControlActive[CONTROL_XBUTTON] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
|
|
swprintf( strBuffer, L"Black = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_BLACK] );
|
|
m_Font12.DrawText( 490, 116, g_ControlActive[CONTROL_BLACKBUTTON] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"B = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_B] );
|
|
m_Font12.DrawText( 490, 134, g_ControlActive[CONTROL_BBUTTON] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"A = %d", m_pGamepad->bAnalogButtons[XINPUT_GAMEPAD_A] );
|
|
m_Font12.DrawText( 490, 152, g_ControlActive[CONTROL_ABUTTON] ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
|
|
swprintf( strBuffer, L"RightStick.x = %d", m_pGamepad->sThumbRX );
|
|
m_Font12.DrawText( 400, 362, m_pGamepad->fX2!=0.0f ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"RightStick.y = %d", m_pGamepad->sThumbRY );
|
|
m_Font12.DrawText( 400, 380, m_pGamepad->fY2!=0.0f ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
swprintf( strBuffer, L"RightThumb" );
|
|
m_Font12.DrawText( 400, 398, m_pGamepad->wButtons & XINPUT_GAMEPAD_RIGHT_THUMB ? 0xffffff00: 0x80ffffff, strBuffer );
|
|
|
|
m_Font12.End();
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: RenderVibrationTestPage()
|
|
// Desc: Renders the page for testing the gamepad vibration motors.
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::RenderVibrationTestPage()
|
|
{
|
|
// Draw a gradient filled background
|
|
RenderGradientBackground( 0xff0000ff, 0xff000000 );
|
|
|
|
// Draw header
|
|
DrawBox( 64, 50, 576, 93, 0x40000000, 0xff000000 );
|
|
m_Font16.DrawText( 69, 50, 0xffffffff, L"Xbox Controller Tool", XBFONT_LEFT );
|
|
m_Font16.DrawText( 571, 50, 0xffffffff, L"Vibration Test Page", XBFONT_RIGHT );
|
|
m_Font12.DrawText( 571, 75, 0xff808080, L"Press START and BACK for next page", XBFONT_RIGHT );
|
|
|
|
// Draw instructions
|
|
DrawBox( 376, 100, 576, 430, 0x40000000, 0xff000000 );
|
|
m_Font12.DrawText( 381, 100, 0xff808080, L"Use the left and right\n"
|
|
L"triggers to test the\n"
|
|
L"vibration function of\n"
|
|
L"gamepad motors.\n" );
|
|
|
|
// Draw outside box
|
|
DrawBox( 64, 100, 366, 430, 0x00000000, 0xff000000 );
|
|
|
|
// Draw the analog gauges
|
|
m_pd3dDevice->SetTexture( 0, m_xprResource.GetTexture( resource_AnalogGauge_OFFSET ) );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_MODULATE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAOP, D3DTOP_MODULATE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE );
|
|
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_COLOROP, D3DTOP_DISABLE );
|
|
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ADDRESSU, D3DTADDRESS_CLAMP );
|
|
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ADDRESSV, D3DTADDRESS_CLAMP );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, TRUE );
|
|
m_pd3dDevice->SetRenderState( D3DRS_SRCBLEND, D3DBLEND_SRCALPHA );
|
|
m_pd3dDevice->SetRenderState( D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA );
|
|
m_pd3dDevice->SetVertexShader( D3DFVF_XYZRHW|D3DFVF_TEX1 );
|
|
struct VERTEX { D3DXVECTOR4 p; FLOAT tu, tv; };
|
|
VERTEX v[4];
|
|
v[0].p = D3DXVECTOR4( 215-100 - 0.5f, 120 - 0.5f, 0, 0 ); v[0].tu = 0; v[0].tv = 0;
|
|
v[1].p = D3DXVECTOR4( 215-100+256 - 0.5f, 120 - 0.5f, 0, 0 ); v[1].tu = 256; v[1].tv = 0;
|
|
v[2].p = D3DXVECTOR4( 215-100+256 - 0.5f, 120+128 - 0.5f, 0, 0 ); v[2].tu = 256; v[2].tv = 128;
|
|
v[3].p = D3DXVECTOR4( 215-100 - 0.5f, 120+128 - 0.5f, 0, 0 ); v[3].tu = 0; v[3].tv = 128;
|
|
m_pd3dDevice->DrawPrimitiveUP( D3DPT_QUADLIST, 1, v, sizeof(v[0]) );
|
|
v[0].p = D3DXVECTOR4( 215-100 - 0.5f, 260 - 0.5f, 0, 0 ); v[0].tu = 0; v[0].tv = 0;
|
|
v[1].p = D3DXVECTOR4( 215-100+256 - 0.5f, 260 - 0.5f, 0, 0 ); v[1].tu = 256; v[1].tv = 0;
|
|
v[2].p = D3DXVECTOR4( 215-100+256 - 0.5f, 260+128 - 0.5f, 0, 0 ); v[2].tu = 256; v[2].tv = 128;
|
|
v[3].p = D3DXVECTOR4( 215-100 - 0.5f, 260+128 - 0.5f, 0, 0 ); v[3].tu = 0; v[3].tv = 128;
|
|
m_pd3dDevice->DrawPrimitiveUP( D3DPT_QUADLIST, 1, v, sizeof(v[0]) );
|
|
|
|
// Draw the gauge needles
|
|
FLOAT fLeftAngle = 0.85f * (2*m_fLeftMotorSpeed-1);
|
|
FLOAT fRightAngle = 0.85f * (2*m_fRightMotorSpeed-1);
|
|
v[0].p.x = 215 + 92*sinf(fLeftAngle); v[0].p.y = 120 + 111 - 92*cosf(fLeftAngle);
|
|
v[1].p.x = 215 + 48*sinf(fLeftAngle); v[1].p.y = 120 + 111 - 48*cosf(fLeftAngle);
|
|
v[2].p.x = 215 + 92*sinf(fRightAngle); v[2].p.y = 260 + 111 - 92*cosf(fRightAngle);
|
|
v[3].p.x = 215 + 48*sinf(fRightAngle); v[3].p.y = 260 + 111 - 48*cosf(fRightAngle);
|
|
m_pd3dDevice->SetTexture( 0, NULL );
|
|
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, FALSE );
|
|
m_pd3dDevice->DrawPrimitiveUP( D3DPT_LINELIST, 2, v, sizeof(v[0]) );
|
|
|
|
// Draw the motor text
|
|
WCHAR strBuffer[80];
|
|
swprintf( strBuffer, L"%d%%", (WORD)(100*m_fLeftMotorSpeed) );
|
|
m_Font16.DrawText( 215+40, 120+100, 0xffffffff, L"Left Motor: ", XBFONT_RIGHT );
|
|
m_Font16.DrawText( 215+40, 120+100, 0xffffff00, strBuffer, XBFONT_LEFT );
|
|
|
|
swprintf( strBuffer, L"%d%%", (WORD)(100*m_fRightMotorSpeed) );
|
|
m_Font16.DrawText( 215+40, 260+100, 0xffffffff, L"Right Motor: ", XBFONT_RIGHT );
|
|
m_Font16.DrawText( 215+40, 260+100, 0xffffff00, strBuffer, XBFONT_LEFT );
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: RenderDeadZoneCalibrationPage()
|
|
// Desc: Renders the page for calibrating the thumbsticks' deadzone.
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::RenderDeadZoneCalibrationPage()
|
|
{
|
|
// Draw a gradient filled background
|
|
RenderGradientBackground( 0xff0000ff, 0xff000000 );
|
|
|
|
// Draw header
|
|
DrawBox( 64, 50, 576, 93, 0x40000000, 0xff000000 );
|
|
m_Font16.DrawText( 69, 50, 0xffffffff, L"Xbox Controller Tool", XBFONT_LEFT );
|
|
m_Font16.DrawText( 571, 50, 0xffffffff, L"Deadzone Calibration Page", XBFONT_RIGHT );
|
|
m_Font12.DrawText( 571, 75, 0xff808080, L"Press START and BACK for next page", XBFONT_RIGHT );
|
|
|
|
FLOAT fBoxCenterX = 204.0f;
|
|
FLOAT fBoxCenterY = 240.0f;
|
|
FLOAT fBoxRadius = 140.0f;
|
|
FLOAT fDeadZone = m_fDeadZone * fBoxRadius;
|
|
|
|
// Draw outside box
|
|
DrawBox( fBoxCenterX - fBoxRadius, fBoxCenterY - fBoxRadius,
|
|
fBoxCenterX + fBoxRadius, fBoxCenterY + fBoxRadius,
|
|
0x00000000, 0xff000000 );
|
|
|
|
// Draw inside box
|
|
DrawBox( fBoxCenterX - fDeadZone, fBoxCenterY - fDeadZone,
|
|
fBoxCenterX + fDeadZone, fBoxCenterY + fDeadZone,
|
|
0x00000000, 0xffffffff );
|
|
|
|
// Draw left thumb stick in red
|
|
FLOAT fThumbLX = fBoxCenterX + fBoxRadius*(m_pGamepad->sThumbLX+0.5f)/32767.5f;
|
|
FLOAT fThumbLY = fBoxCenterY - fBoxRadius*(m_pGamepad->sThumbLY+0.5f)/32767.5f;
|
|
DrawBox( fThumbLX-1, fThumbLY-8, fThumbLX+1, fThumbLY+8, 0xffff0000, 0xffff0000 );
|
|
DrawBox( fThumbLX-8, fThumbLY-1, fThumbLX+8, fThumbLY+1, 0xffff0000, 0xffff0000 );
|
|
|
|
// Draw right thumb stick in green
|
|
FLOAT fThumbRX = fBoxCenterX + fBoxRadius*(m_pGamepad->sThumbRX+0.5f)/32767.5f;
|
|
FLOAT fThumbRY = fBoxCenterY - fBoxRadius*(m_pGamepad->sThumbRY+0.5f)/32767.5f;
|
|
DrawBox( fThumbRX-1, fThumbRY-8, fThumbRX+1, fThumbRY+8, 0xff00ff00, 0xff00ff00 );
|
|
DrawBox( fThumbRX-8, fThumbRY-1, fThumbRX+8, fThumbRY+1, 0xff00ff00, 0xff00ff00 );
|
|
|
|
// Draw instructions
|
|
DrawBox( 354, 100, 576, 380, 0x40000000, 0xff000000 );
|
|
m_Font12.DrawText( 359, 100, 0xff808080, L"Move thumbsticks to test\n"
|
|
L"sensitivty around the\n"
|
|
L"the deadzone (defined by\n"
|
|
L"the white box). Let them\n"
|
|
L"snap back and notice how\n"
|
|
L"the controls adapt over\n"
|
|
L"time allowing for a smaller\n"
|
|
L"deadzone.\n\n"
|
|
L"Use DPad to control the\n"
|
|
L"deadzone size.");
|
|
|
|
WCHAR strBuffer[80];
|
|
swprintf( strBuffer, L"Deadzone: %ld (%ld%%)", (LONG)(32768*m_fDeadZone), (LONG)(100*m_fDeadZone) );
|
|
m_Font12.DrawText( 359, 360, 0xffffffff, strBuffer );
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: RenderButtonQuantizationPage()
|
|
// Desc: Renders the page for testing the quantization of the controls
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::RenderButtonQuantizationPage()
|
|
{
|
|
// Draw a gradient filled background
|
|
RenderGradientBackground( 0xff0000ff, 0xff000000 );
|
|
|
|
// Draw header
|
|
DrawBox( 64, 50, 576, 93, 0x40000000, 0xff000000 );
|
|
m_Font16.DrawText( 69, 50, 0xffffffff, L"Xbox Controller Tool", XBFONT_LEFT );
|
|
m_Font16.DrawText( 571, 50, 0xffffffff, L"Control Quantization Page", XBFONT_RIGHT );
|
|
m_Font12.DrawText( 571, 75, 0xff808080, L"Press START and BACK for next page", XBFONT_RIGHT );
|
|
|
|
// Draw instructions
|
|
DrawBox( 374, 100, 576, 400, 0x40000000, 0xff000000 );
|
|
m_Font12.DrawText( 379, 100, 0xff808080, L"Analog controls have 8\n"
|
|
L"bits of precision. Press\n"
|
|
L"the analog buttons and\n"
|
|
L"move the thumbsticks to\n"
|
|
L"see what values are\n"
|
|
L"quantized. Hit the START\n"
|
|
L"button to reset the values.");
|
|
|
|
// Draw outside box
|
|
DrawBox( 64, 100, 364, 400, 0x00000000, 0xff000000 );
|
|
|
|
// Colors for rendering the quantized values
|
|
DWORD adwColors[8] =
|
|
{
|
|
0xff80ff80, // Light green
|
|
0xffff8080, // Light red
|
|
0xff8080ff, // Light blue
|
|
0xffffff80, // Light yellow
|
|
0xff000000, // Black
|
|
0xffffffff, // White
|
|
0xff000000, // Black
|
|
0xff000000, // Black
|
|
};
|
|
|
|
// Count of unique quantized values for each of the 8 analog controls and
|
|
// the 4 thumbstick axes.
|
|
DWORD adwQuantizationCount[12] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
|
|
|
|
// Display quantized button values
|
|
m_Font12.DrawText( 150, 100, 0xffffffff, L"Buttons", XBFONT_CENTER_X );
|
|
|
|
for( DWORD x=0; x<8; x++ )
|
|
{
|
|
// Draw gray bar
|
|
DrawBox( 20.0f*x+78.0f, 120.0f, 20.0f*x+82.0f, 376.0f, 0xff404040, 0xff404040 );
|
|
|
|
for( DWORD y=0; y<256; y++ )
|
|
{
|
|
// Highlight recorded values
|
|
if( m_pQuantizedButtonValues[y] & (1<<x) )
|
|
{
|
|
DrawBox( 20.0f*x+76.0f, 376.0f-y, 20.0f*x+84.0f, 376.0f-y, adwColors[x], adwColors[x] );
|
|
adwQuantizationCount[x]++;
|
|
}
|
|
|
|
// Highlight the current value
|
|
DrawBox( 20.0f*x+74.0f, 375.0f-m_pGamepad->bAnalogButtons[x],
|
|
20.0f*x+86.0f, 377.0f-m_pGamepad->bAnalogButtons[x],
|
|
adwColors[x], adwColors[x] );
|
|
}
|
|
|
|
// Draw label
|
|
m_Font12.DrawText( 20.0f*x+80.0f, 376.0f, 0xffffffff, L"A\0B\0X\0Y\0B\0W\0L\0R\0"+2*x, XBFONT_CENTER_X );
|
|
}
|
|
|
|
// Display quantized thumbstick values
|
|
m_Font12.DrawText( 305.0f, 100.0f, 0xffffffff, L"Thumbsticks", XBFONT_CENTER_X );
|
|
|
|
for( x=0; x<4; x++ )
|
|
{
|
|
// Draw gray bar
|
|
DrawBox( 30.0f*x+258.0f, 120.0f, 30.0f*x+262.0f, 376.0f, 0xff404040, 0xff404040 );
|
|
|
|
for( DWORD y=0; y<256; y++ )
|
|
{
|
|
// Highlight recorded values
|
|
if( m_pQuantizedThumbStickValues[y] & (1<<x) )
|
|
{
|
|
DrawBox( 30.0f*x+256.0f, 376.0f-y, 30.0f*x+264, 376.0f-y, 0xffffffff, 0xffffffff );
|
|
adwQuantizationCount[8+x]++;
|
|
}
|
|
|
|
// Highlight the current value
|
|
BYTE val = 0;
|
|
if( x == 0 ) val = (32768 + m_pGamepad->sThumbLX) >> 8;
|
|
if( x == 1 ) val = (32768 + m_pGamepad->sThumbLY) >> 8;
|
|
if( x == 2 ) val = (32768 + m_pGamepad->sThumbRX) >> 8;
|
|
if( x == 3 ) val = (32768 + m_pGamepad->sThumbRY) >> 8;
|
|
DrawBox( 30.0f*x+254.0f, 375.0f-val, 30.0f*x+266.0f, 377.0f-val, 0xffff0000, 0xffff0000 );
|
|
}
|
|
|
|
// Draw label
|
|
m_Font12.DrawText( 30.0f*x+260.0f, 376.0f, 0xffffffff, L"LX\0LY\0RX\0RY\0"+3*x, XBFONT_CENTER_X );
|
|
}
|
|
|
|
// Show the number of unique values each analog control has hit
|
|
WCHAR strBuffer[80];
|
|
m_Font12.DrawText( 379, 260, 0xff808080, L"Count of unique values:" );
|
|
|
|
m_Font12.DrawText( 399, 280, 0xff808080, L"A\nB\nX\nY\nB\nW\n" );
|
|
swprintf( strBuffer, L"%ld\n%ld\n%ld\n%ld\n%ld\n%ld\n",
|
|
adwQuantizationCount[0], adwQuantizationCount[1],
|
|
adwQuantizationCount[2], adwQuantizationCount[3],
|
|
adwQuantizationCount[4], adwQuantizationCount[5] );
|
|
m_Font12.DrawText( 419, 280, 0xffffffff, strBuffer );
|
|
|
|
m_Font12.DrawText( 485, 280, 0xff808080, L"LT\nRT\nLX\nLY\nRX\nRY\n" );
|
|
swprintf( strBuffer, L"%ld\n%ld\n%ld\n%ld\n%ld\n%ld\n",
|
|
adwQuantizationCount[6], adwQuantizationCount[7],
|
|
adwQuantizationCount[8], adwQuantizationCount[9],
|
|
adwQuantizationCount[10], adwQuantizationCount[11] );
|
|
m_Font12.DrawText( 515, 280, 0xffffffff, strBuffer );
|
|
|
|
return S_OK;
|
|
}
|
|
|
|
|
|
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Name: Render()
|
|
// Desc: Sets up render states, clears the viewport, and renders the scene.
|
|
//-----------------------------------------------------------------------------
|
|
HRESULT CXBoxSample::Render()
|
|
{
|
|
if( m_dwNumInsertedGamepads != 1 )
|
|
{
|
|
RenderInsertRemoveControllerPage();
|
|
}
|
|
else
|
|
{
|
|
switch( m_AppState )
|
|
{
|
|
case APPSTATE_CONTROLTEST:
|
|
RenderControlTestPage();
|
|
break;
|
|
|
|
case APPSTATE_VIBRATIONTEST:
|
|
RenderVibrationTestPage();
|
|
break;
|
|
|
|
case APPSTATE_DEADZONECALIBRATION:
|
|
RenderDeadZoneCalibrationPage();
|
|
break;
|
|
|
|
case APPSTATE_BUTTONQUANTIZATION:
|
|
RenderButtonQuantizationPage();
|
|
break;
|
|
}
|
|
}
|
|
|
|
// Present the scene
|
|
m_pd3dDevice->Present( NULL, NULL, NULL, NULL );
|
|
|
|
return S_OK;
|
|
}
|
|
|