> ## Documentation Index
> Fetch the complete documentation index at: https://devdocs.xbox.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Portabilidade do XInput para o GameInput

> Portabilidade do XInput para o GameInput

<a id="introductionSection" />

Portar do XInput para o GameInput é a portabilidade menos complicada entre todas as APIs legadas. Isso ocorre porque o GameInput foi fortemente influenciado pelo modelo de programação simples (e fácil de usar) do XInput e, portanto, muitas APIs do XInput são mapeadas 1:1 com funções equivalentes no GameInput.

<a id="keyDifferencesSection" />

## Principais diferenças

As principais diferenças entre o XInput e o GameInput são discutidas nas seções a seguir.

<a id="cVsCppSection" />

### C vs. C++

A API XInput é uma coleção de funções C simples. O GameInput, por outro lado, é C++ e usa interfaces (assim como as APIs de gráficos e áudio). Na prática, isso não complica o código que usa a API GameInput, não afeta o desempenho e tem algumas vantagens que se tornam evidentes à medida que você se familiariza com o funcionamento do GameInput.

É importante entender que, embora essas interfaces possam parecer COM, elas não são. Apenas um entendimento básico de contagem de referências é necessário para usar essas interfaces. Para obter mais informações, confira a [seção Interfaces do tópico Fundamentos do GameInput](/pt-BR/build/core-features/common/input/overviews/input-fundamentals#interfacesSection).

<a id="gettingInputSection" />

### Obtenção de entrada

No XInput, a maioria dos jogos percorre os índices de usuário em loop até encontrar um com um dispositivo conectado e, em seguida, o estado é lido desse dispositivo. Os jogos geralmente lembram o índice de usuário para não precisarem percorrer o loop na próxima vez. Por exemplo, o código a seguir é típico de um jogo que solicita ao usuário que "pressione A" no controle:

```c++ theme={null}
// This function looks for a gamepad that currently has the "A" button pressed.
void FindActiveGamepad()
{
    for (DWORD index = 0; index < XUSER_MAX_COUNT; index++)
    {
        XINPUT_STATE state;
        if (XInputGetState(index, &state) == ERROR_SUCCESS)
        {
            if (state.Gamepad.wButtons & XINPUT_GAMEPAD_A)
            {
                // Found the user's gamepad at this index.
            }
        }
    }
}
```

No GameInput, você primeiro obtém a entrada sem especificar um dispositivo e pode consultar de qual dispositivo a entrada veio, se quiser. O código é parecido, mas eliminar a necessidade de enumeração explícita de dispositivos pode levar a algoritmos mais simples.

```c++ theme={null}
// This function looks for a gamepad that currently has the "A" button pressed.
void FindActiveGamepad(IGameInput * gameInput)
{
    // This checks for input from all gamepads simultaneously.
    IGameInputReading * reading;
    if (SUCCEEDED(gameInput->GetCurrentReading(GameInputKindGamepad, nullptr, &reading)))
    {
        GameInputGamepadState state;
        reading->GetGamepadState(&state);

        if (state.buttons & GameInputGamepadA)
        {
            // Found the user's gamepad.  At this point we can
            // get the device that generated this input, and then
            // pass that into future calls to the GetCurrentReading
            // method to receive input only from that gamepad.
        }

        reading->Release():
    }
}
```

O código não é tão simples quanto o do XInput, mas é muito parecido. À medida que você se familiarizar com a API GameInput, verá como esse modelo oferece opções poderosas para lidar com a entrada que não existem no XInput.

Também vale observar que o XInput retorna os valores analógicos dos gatilhos como tipo **BYTE** e os valores analógicos dos direcionais analógicos como tipo **SHORT**. Com a API GameInput, esses valores analógicos são retornados como valores **float** de 0 a 1 (gatilhos) ou de -1 a 1 (direcionais analógicos).

<a id="rumbleFeedbackSection" />

### Resposta de vibração

No XInput, os jogos simplesmente chamam`XInputSetState` para enviar comandos de vibração a um dispositivo. No GameInput, os jogos precisam obter a instância de [IGameInputDevice](/pt-BR/reference/input/gameinput/interfaces/igameinputdevice/igameinputdevice) do dispositivo e, em seguida, chamar o método [SetRumbleState](/pt-BR/reference/input/gameinput/interfaces/igameinputdevice/methods/igameinputdevice_setrumblestate) dela. O uso é semelhante entre esses dois métodos. Este é um exemplo de quando você chamará funções na interface do dispositivo, em vez de usá-la apenas como identificador de dispositivo.

<a id="appFocusSection" />

### Foco do aplicativo

No console, o GameInput fornece entrada a um aplicativo somente quando ele está em foco. Caso contrário, o estado retornado contém valores neutros ou de "repouso", como se o usuário não estivesse tocando no dispositivo. Isso elimina a necessidade de código de entrada extra para lidar com a mudança de foco (por exemplo, chamar`XInputEnable`).

No PC, por padrão, a entrada vai para todos os processos. No futuro, esse comportamento poderá ser alterado usando o método [SetFocusPolicy](/pt-BR/reference/input/gameinput/interfaces/igameinput/methods/igameinput_setfocuspolicy).

<a id="xinputWrapperSection" />

## O wrapper XInputOnGameInput

O Microsoft Game Development Kit (GDK) é fornecido com um arquivo de cabeçalho chamado`XInputOnGameInput.h` que contém uma implementação da API XInput sobre o GameInput. Recomendamos portar diretamente para o GameInput, especialmente se você quiser teclado e mouse ou outros dispositivos de entrada. No entanto, o wrapper XInputOnGameInput pode ser usado para ajudar a iniciar um esforço inicial de portabilidade sem exigir alterações no código XInput existente.

Para usar o wrapper XInputOnGameInput, basta substituir este código:

```c++ theme={null}
#include <XInput.h>
```

por este código:

```c++ theme={null}
#include <XInputOnGameInput.h>
using namespace XInputOnGameInput;
```

e, em seguida, recompilar o código.

A implementação do código do wrapper XInput está inteiramente no arquivo de cabeçalho, portanto, também pode ser examinada como exemplo de uso da API GameInput e/ou modificada conforme necessário.

<a id="wrapperDifferencesSection" />

### Diferenças entre o XInput e o XInputOnGameInput

Em geral, o wrapper XInputOnGameInput é um substituto direto para a API XInput legada. No entanto, há algumas pequenas diferenças:

* Para simplificar, apenas o suporte a dispositivos gamepad foi codificado no wrapper. Se você precisar dar suporte a outros dispositivos, como volantes de corrida ou arcade sticks, use o GameInput diretamente ou adicione suporte a esses dispositivos no código do XInputOnGameInput.

* O wrapper retornará a entrada do gamepad somente quando o jogo estiver em foco. Quando o jogo não estiver em foco, qualquer estado de gamepad retornado é definido com valores neutros ou de "repouso", como se o usuário não estivesse tocando no gamepad. Isso é feito independentemente de quaisquer chamadas a`XInputEnable` (ou da falta delas).

* O valor de`XUSER_MAX_COUNT` foi aumentado de 4 para 8. Em geral, isso deve ser transparente para a maior parte do código XInput legado. No entanto, revise cuidadosamente qualquer uso da função`XInputGetKeystroke` no seu código para ajudar a garantir que nada esteja codificado para presumir um valor máximo de 4 retornado no membro`UserIndex` da estrutura`XINPUT_KEYSTROKE`. Caso contrário, poderá ocorrer uma saturação de buffer.

* Algumas novas funções foram adicionadas (veja a seguir), que devem interessar apenas se você pretende continuar usando o wrapper XInput em código de produção.

<a id="productionWrapperUseSection" />

### Uso do XInputOnGameInput em código de produção

O wrapper XInputOnGameInput foi escrito para ser de alto desempenho e livre de bloqueio, herdando todas as otimizações de desempenho da API GameInput e, portanto, é adequado para uso em código de produção. Ele também herda o suporte mais amplo a dispositivos do GameInput (como gamepads HID populares) e adiciona as seguintes novas funções à API:

* **`XInputSetStateEx`** é semelhante a`XInputSetState`, mas adiciona suporte aos motores dos gatilhos.

* **`XInputGetStateWithToken`** é semelhante a`XInputGetState`, mas permite que o chamador forneça um token de pipeline de quadro D3DX para associar uma leitura de entrada específica a um quadro gráfico para análise posterior no PIX.

  > \[!NOTE]
  > Na versão May Preview,`XInputGetStateWithToken` atualmente se comporta de forma idêntica a`XInputGetState`, porque o código subjacente do GameInput não está totalmente implementado.

* **`XInputGetDeviceId`** retorna o`APP_LOCAL_DEVICE_ID` do dispositivo em um determinado índice de usuário. Passar essa ID para o método [FindDeviceFromId](/pt-BR/reference/input/gameinput/interfaces/igameinput/methods/igameinput_finddevicefromid) em [IGameInput](/pt-BR/reference/input/gameinput/interfaces/igameinput/igameinput) retorna o [IGameInputDevice](/pt-BR/reference/input/gameinput/interfaces/igameinputdevice/igameinputdevice) correspondente a esse índice de usuário. Isso pode então ser usado para acessar funcionalidades adicionais da API GameInput que não são expostas pelo wrapper XInput.

<a id="optimizingSection" />

#### Otimização do código do wrapper

Por padrão, o wrapper XInputOnGameInput é configurado para ser um substituto direto compatível com a API XInput legada. Os jogos que não exigem comportamento 100% compatível podem ajustar o comportamento e o desempenho do wrapper definindo qualquer uma das seguintes macros de pré-processador:

##### XINPUT\_ON\_GAMEINPUT\_EXPLICIT\_INITIALIZATION

Por padrão, o wrapper XInput inicializa de forma lenta a API GameInput subjacente automaticamente na primeira vez em que qualquer uma das funções do wrapper é chamada. Isso garante a compatibilidade direta com o código XInput existente, mas tem várias pequenas desvantagens:

1. O tempo de execução da primeira chamada de função do wrapper XInput será maior do que o normal.

2. Toda função do wrapper XInput precisa verificar se a inicialização lenta foi realizada sempre que é chamada. Esse é um teste simples de uma variável global, portanto, o preditor de desvios deve amenizar o custo, mas é uma sobrecarga extra.

3. Embora nunca deva falhar, não há como saber se a inicialização lenta da API GameInput subjacente foi bem-sucedida.

4. A instância subjacente de [IGameInput](/pt-BR/reference/input/gameinput/interfaces/igameinput/igameinput) não é liberada até que as variáveis globais do wrapper XInput sejam limpas (seja devido ao descarregamento do módulo ou ao encerramento do processo).

Os jogos podem assumir o controle manual da inicialização e do desligamento do wrapper definindo a macro`XINPUT_ON_GAMEINPUT_EXPLICIT_INITIALIZATION`. Isso adiciona duas novas funções,`XInputOnGameInputInitialize` e`XInputOnGameInputUninitialize`, que podem ser chamadas para controlar com precisão quando a inicialização e o desligamento ocorrem.

##### XINPUT\_ON\_GAMEINPUT\_NO\_XINPUTENABLE

O código necessário para implementar a função`XInputEnable` adiciona sobrecarga extra a cada chamada das funções`XInputGetState`,`XInputGetStateWithToken`,`XInputSetState`,`XInputSetStateEx` e`XInputGetKeystroke`. Se o seu código não chama`XInputEnable`, ou se essa chamada puder ser facilmente eliminada do seu código, definir a macro`XINPUT_ON_GAMEINPUT_NO_XINPUTENABLE` removerá o suporte a`XInputEnable` e a sobrecarga associada. De qualquer forma, o código subjacente do GameInput executa automaticamente a funcionalidade de`XInputEnable` nas mudanças de foco, portanto, a maioria dos jogos vai querer definir essa macro, se puder.

##### XINPUT\_ON\_GAMEINPUT\_NO\_XINPUTGETKEYSTROKE

O código necessário para implementar a função`XInputGetKeystroke` adiciona algumas funções e variáveis extras à implementação do wrapper. Ele não adiciona sobrecarga a nenhuma das outras funções da API XInput, mas, se o seu código não chama`XInputGetKeystroke`, você pode definir a macro`XINPUT_ON_GAMEINPUT_NO_XINPUTGETKEYSTROKE` para diminuir ligeiramente o tamanho do código/dados do wrapper XInput.

<a id="seeAlsoSection" />

## Documentação de referência da API

* [GameInput (conteúdo da API)](/pt-BR/reference/input/gameinput/gameinput_members)
* [XInputOnGameInput (conteúdo da API)](/pt-BR/reference/input/xinputongameinput/xinputongameinput_members)

## Confira também

[Visão geral do GameInput](/pt-BR/build/core-features/common/input/overviews/input-overview)

[Referência da API GameInput](/pt-BR/reference/input/gc-reference-input-toc)

[Microsoft Game Development Kit](/pt-BR/services/playfab/sdks/platforms/gdk)


## Related topics

- [Guias de portabilidade para o XBOX GDK](/pt-BR/home/build-first-title/porting-guides.md)
- [Porting from XInput to GameInput](/build/core-features/common/input/porting/input-porting-xinput.md)
- [Portabilidad de XInput a GameInput](/es/build/core-features/common/input/porting/input-porting-xinput.md)
- [从 XInput 移植到 GameInput](/zh-CN/build/core-features/common/input/porting/input-porting-xinput.md)
- [XInput에서 GameInput으로 포팅](/ko/build/core-features/common/input/porting/input-porting-xinput.md)
