Introdução ao C++/WinRT

 

 

O C++/WinRT é uma projeção de linguagem C++17 moderna totalmente padrão para APIs Windows Runtime (WinRT), implementada como uma biblioteca baseada em arquivos de cabeçalho e projetada para fornecer acesso de primeira classe à API moderna do Windows. Com o C++/WinRT, você pode criar e consumir APIs Windows Runtime usando qualquer compilador C++17 compatível com padrões. O SDK do Windows inclui C++/WinRT; foi introduzido na versão 10.0.17134.0 (Windows 10, versão 1803).

C++/WinRT é o substituto recomendado pela Microsoft para a projeção da linguagem C++/CX e a Windows Runtime C++ Template Library (WRL). A lista completa de tópicos sobre C++/WinRT inclui informações sobre interoperação e portabilidade de C++/CX e WRL.

Important

Algumas das partes mais importantes do C++/WinRT a serem observadas são descritas nas seções de suporte do SDK para C++/WinRT e Visual Studio suporte para C++/WinRT, XAML, a extensão VSIX e o pacote NuGet.

Veja também onde posso encontrar aplicativos de exemplo do C++/WinRT?.

Projeções de linguagem

O Windows Runtime é baseado em APIs COM (Component Object Model) e foi projetado para ser acessado por meio de projeções de linguagem. Uma projeção oculta os detalhes do COM e fornece uma experiência de programação mais natural para um determinado idioma.

A projeção da linguagem C++/WinRT no conteúdo de referência da API Windows Runtime

Quando estiver navegando Windows Runtime APIs, clique na caixa de combinação Idioma no canto superior direito e selecione C++/WinRT para exibir blocos de sintaxe de API conforme eles aparecem na projeção de linguagem C++/WinRT.

Visual Studio suporte para C++/WinRT, XAML, a extensão VSIX e o pacote NuGet

Para Visual Studio suporte, você precisará Visual Studio 2022 ou Visual Studio 2019 ou Visual Studio 2017 (pelo menos a versão 15.6; recomendamos pelo menos 15.7). No instalador do Visual Studio, instale a carga de trabalho desenvolvimento da Plataforma Universal do Windows. Em Detalhes da Instalação>Desenvolvimento da Plataforma Universal do Windows, marque as opções Ferramentas da Plataforma Universal do Windows C++ (v14x) caso ainda não o tenha feito. E, em Windows Configurações>Privacidade e segurança (Windows 10: Atualização & Segurança) >Para desenvolvedores, habilite a opção Modo de Desenvolvedor (Windows 10: não a opção Instalar aplicativos de qualquer origem).

Embora seja recomendável desenvolver com as versões mais recentes do Visual Studio e do SDK do Windows, se você estiver usando uma versão do C++/WinRT que foi enviada com o SDK do Windows antes da 10.0.17763.0 (Windows 10, versão 1809), então, para usar os cabeçalhos de namespaces Windows mencionados acima, você precisará de um mínimo Windows versão de destino do SDK no projeto 10.0.17134.0 (Windows 10, versão 1803).

O Visual Studio 2022 já vem com modelos de projeto e de item do C++/WinRT integrados, para que você possa começar a desenvolver com C++/WinRT na hora. Ele também vem com a visualização de depuração nativa (natvis) do Visual Studio para tipos projetados do C++/WinRT, proporcionando uma experiência semelhante à da depuração em C#. O Natvis é automático para compilações de depuração. Para obter mais informações, consulte visualização nativa de depuração do Visual Studio para C++/WinRT.

Para versões mais antigas do Visual Studio, você desejará baixar e instalar a versão mais recente da VSIX (Extensão de Visual Studio do C++/WinRT) do Visual Studio Marketplace.

  • A extensão VSIX fornece modelos de projeto e de item do C++/WinRT no Visual Studio.
  • Além disso, ela oferece a natvis (visualização de depuração nativa do Visual Studio) de tipos projetados em C++/WinRT.

Os modelos de projeto Visual Studio para C++/WinRT são descritos nas seções abaixo. Quando você cria um novo projeto C++/WinRT com a versão mais recente da extensão VSIX instalada, o novo projeto C++/WinRT instala automaticamente o pacote NuGet Microsoft.Windows.CppWinRT. O pacote NuGet Microsoft.Windows.CppWinRT fornece suporte de compilação para C++/WinRT (propriedades e alvos do MSBuild), tornando seu projeto portátil entre uma máquina de desenvolvimento e um agente de build (no qual apenas o pacote NuGet, e não a extensão VSIX, está instalado).

Como alternativa, você pode converter um projeto existente instalando manualmente o pacote NuGet Microsoft.Windows.CppWinRT. Depois de instalar (ou atualizar para) a versão mais recente da extensão VSIX, abra o project existente no Visual Studio, clique em Project>Manage NuGet Packages...>Navegue, digite ou cole Microsoft.Windows. CppWinRT na caixa de pesquisa, selecione o item nos resultados da pesquisa e clique em Instalar para instalar o pacote para esse project. Depois de adicionar o pacote, o projeto passará a ter suporte do MSBuild para C++/WinRT, incluindo a invocação da ferramenta cppwinrt.exe.

Important

Se você tiver projetos criados com (ou atualizados para trabalhar) uma versão da extensão VSIX anterior à 1.0.190128.4, consulte versões anteriores da extensão VSIX. Essa seção contém informações importantes sobre a configuração de seus projetos, que você precisará saber para atualizá-los para usar a versão mais recente da extensão VSIX.

  • Como o C++/WinRT usa recursos do padrão C++17, o pacote NuGet define a propriedade de projeto C/C++>Language>C++ Language Standard>ISO C++17 Standard (/std:c++17) em Visual Studio.
  • Ele também adiciona a opção do compilador /bigobj .
  • Ele adiciona a opção do compilador /await para habilitar co_await.
  • Ele instrui o compilador XAML a emitir o codegen C++/WinRT.
  • Talvez você também deseje definir o modo de conformidade: Sim (/permissive-), o que restringe ainda mais seu código a ser compatível com padrões.
  • Outra propriedade do projeto a ser observada é C/C++>General>Tratar avisos como erros. Defina isso como Sim(/WX) ou Não (/WX-) a gosto. Às vezes, os arquivos de origem cppwinrt.exe gerados pela ferramenta geram avisos até que você adicione sua implementação a eles.

Com o sistema configurado conforme descrito acima, você poderá criar e criar ou abrir um projeto C++/WinRT em Visual Studio e implantá-lo.

A partir da versão 2.0, o pacote NuGet Microsoft.Windows.CppWinRT inclui a ferramenta cppwinrt.exe. Você pode apontar a ferramenta cppwinrt.exe para um arquivo de metadados do Windows Runtime (.winmd) para gerar uma biblioteca C++ padrão baseada em arquivos de cabeçalho que expõe as APIs descritas nos metadados para uso em código C++/WinRT. Os arquivos de metadados do Windows Runtime (.winmd) fornecem uma forma canônica de descrever a superfície da API do Windows Runtime. Apontando cppwinrt.exe para metadados, você pode gerar uma biblioteca para uso com qualquer classe de runtime implementada em um componente de Windows Runtime de terceiros ou implementada em seu próprio aplicativo. Para obter mais informações, consulte Consumir APIs com C++/WinRT.

Com o C++/WinRT, você também pode implementar suas próprias classes de runtime usando C++padrão, sem recorrer à programação no estilo COM. Para uma classe de runtime, você descreve apenas os tipos em um arquivo IDL e midl.exe e cppwinrt.exe geram os arquivos de código-fonte clichê de implementação para você. Como alternativa, você pode apenas implementar interfaces derivando de uma classe base C++/WinRT. Para obter mais informações, consulte Criação de APIs com C++/WinRT.

Para obter uma lista de opções de personalização para o conjunto de ferramentas cppwinrt.exe por meio das propriedades do projeto, confira o arquivo Leiame do pacote NuGet Microsoft.Windows.CppWinRT.

Você pode identificar um projeto que usa o suporte MSBuild do C++/WinRT pela presença do pacote NuGet Microsoft.Windows.CppWinRT instalado no projeto.

Aqui estão os modelos de projeto Visual Studio fornecidos pela extensão VSIX.

Aplicativo em Branco (C++/WinRT)

Um modelo de projeto para um aplicativo Plataforma Universal do Windows (UWP) que tem uma interface do usuário XAML. Para aplicativos de desktop WinUI 3, use o modelo Aplicativo em Branco, Empacotado (WinUI 3 na Área de Trabalho).

O Visual Studio fornece suporte ao compilador XAML para gerar esqueletos de implementação e de cabeçalho a partir do arquivo IDL (Interface Definition Language) (.idl) subjacente a cada arquivo de marcação XAML. Em um arquivo IDL, defina todas as classes locais de tempo de execução que você deseja referenciar nas páginas XAML do aplicativo e, em seguida, compile o projeto uma vez para gerar modelos de implementação em Generated Files e definições de tipo de stub em Generated Files\sources. Em seguida, use essas definições de tipo stub para referência para implementar suas classes de runtime locais. Consulte Como fatorar classes de tempo de execução em arquivos MIDL (.idl).

O suporte à superfície de design XAML em Visual Studio para C++/WinRT está próximo da paridade com C#. Em Visual Studio, você pode usar a guia Eventos da janela Propriedades para adicionar manipuladores de eventos em um projeto C++/WinRT. Você também pode adicionar manipuladores de eventos ao seu código manualmente– consulte Manipular eventos usando delegados no C++/WinRT para obter mais informações.

Aplicativo Principal (C++/WinRT)

Um modelo de projeto para um aplicativo Plataforma Universal do Windows (UWP) que não usa XAML. Não há nenhum WinUI 3 equivalente a este modelo.

Em vez disso, ele usa o cabeçalho de namespace do Windows do C++/WinRT para o namespace Windows.ApplicationModel.Core. Depois de compilar e executar, clique em um espaço vazio para adicionar um quadrado colorido; em seguida, clique em um quadrado colorido para arrastá-lo.

Aplicativo do Console do Windows (C++/WinRT)

Um modelo de projeto para um aplicativo cliente C++/WinRT para Windows Desktop, com uma interface do usuário do console.

Aplicativo da Área de Trabalho do Windows (C++/WinRT)

Um modelo de projeto para um aplicativo cliente do C++/WinRT para a Área de Trabalho do Windows, que exibe um Windows Runtime Windows.Foundation.Uri dentro de um Win32 MessageBox.

Componente Windows Runtime (C++/WinRT)

Um modelo de projeto para um componente; normalmente para uso em uma Plataforma Universal do Windows (UWP).

Esse modelo demonstra a cadeia de ferramentas midl.exe>cppwinrt.exe, na qual os metadados do Windows Runtime (.winmd) são gerados com base na IDL. Depois, os stubs de implementação e de cabeçalho são gerados com base nesses metadados.

Em um arquivo IDL, defina as classes de runtime em seu componente, sua interface padrão e quaisquer outras interfaces que implementem. Compile o projeto uma vez para gerar module.g.cpp, module.h.cpp, templates de implementação em Generated Files e definições de tipos stub em Generated Files\sources. Em seguida, use essas definições de tipo stub para referência para implementar as classes de runtime em seu componente. Consulte Como separar classes de runtime em arquivos MIDL (.idl).

Agrupe o binário compilado do componente do Windows Runtime e seu .winmd com o aplicativo UWP os consumindo.

Versões anteriores da extensão VSIX

Recomendamos que você instale (ou atualize para) a versão mais recente da extensão VSIX. Ele é configurado para se atualizar por padrão. Se você fizer isso e tiver projetos que foram criados com uma versão da extensão VSIX anterior à 1.0.190128.4, esta seção conterá informações importantes sobre como atualizar esses projetos para trabalhar com a nova versão. Se você não atualizar, ainda encontrará as informações nesta seção úteis.

Em termos das versões com suporte do Windows SDK e do Visual Studio, e da configuração do Visual Studio, as informações na seção Suporte do Visual Studio para C++/WinRT, XAML, a extensão VSIX e o pacote NuGet acima se aplicam às versões anteriores da extensão VSIX. As informações abaixo descrevem diferenças importantes em relação ao comportamento e à configuração de projetos criados com (ou atualizados para trabalhar com) versões anteriores.

Criado anteriormente à 1.0.181002.2

Se o projeto foi criado com uma versão da extensão VSIX anterior à 1.0.181002.2, o suporte ao build do C++/WinRT foi integrado a essa versão da extensão VSIX. Seu projeto tem a <CppWinRTEnabled>true</CppWinRTEnabled> propriedade definida no .vcxproj arquivo.

<Project ...>
    <PropertyGroup Label="Globals">
        <CppWinRTEnabled>true</CppWinRTEnabled>
...

Você pode atualizar seu projeto instalando manualmente o pacote NuGet Microsoft.Windows.CppWinRT. Depois de instalar (ou atualizar para) a versão mais recente da extensão VSIX, abra o project em Visual Studio, clique em Project>Manage NuGet Packages...>Navegue, digite ou cole Microsoft.Windows. CppWinRT na caixa de pesquisa, selecione o item nos resultados da pesquisa e clique em Instalar para instalar o pacote para o project.

Criado com (ou atualizado para) entre 1.0.181002.2 e 1.0.190128.3

Se o seu projeto foi criado com uma versão da extensão VSIX entre 1.0.181002.2 e 1.0.190128.3, inclusive, então o pacote NuGet Microsoft.Windows.CppWinRT foi instalado automaticamente no projeto pelo modelo de projeto. Você também pode ter atualizado um projeto mais antigo para usar uma versão da extensão VSIX nesse intervalo. Se você fez isso, então, como o suporte de compilação também ainda estava presente nas versões da extensão VSIX nesse intervalo, seu projeto atualizado pode ou não ter o pacote NuGet Microsoft.Windows.CppWinRT instalado.

Para atualizar seu projeto, siga as instruções na seção anterior e certifique-se de que seu projeto tenha o pacote NuGet Microsoft.Windows.CppWinRT instalado.

Configurações de atualização inválidas

Com a versão mais recente da extensão VSIX, não é válido que um projeto tenha a propriedade <CppWinRTEnabled>true</CppWinRTEnabled> se ele não tiver também o pacote NuGet Microsoft.Windows.CppWinRT instalado. Um projeto com essa configuração gera a mensagem de erro de compilação: "O VSIX do C++/WinRT não fornece mais suporte à compilação do projeto. Adicione uma referência de projeto ao pacote NuGet Microsoft.Windows.CppWinRT".

Conforme mencionado acima, um projeto C++/WinRT agora precisa ter o pacote NuGet instalado nele.

Como o elemento <CppWinRTEnabled> agora está obsoleto, se desejar, você pode editar seu .vcxproj e excluir o elemento. Não é estritamente necessário, mas é uma opção.

Além disso, se o seu .vcxproj contiver <RequiredBundles>$(RequiredBundles);Microsoft.Windows.CppWinRT</RequiredBundles>, você poderá removê-lo para compilar sem exigir que a extensão VSIX do C++/WinRT esteja instalada.

Suporte do SDK para C++/WinRT

Embora agora esteja presente apenas por motivos de compatibilidade, a partir da versão 10.0.17134.0 (Windows 10, versão 1803), o SDK do Windows contém uma biblioteca C++ padrão baseada em arquivo de cabeçalho para consumir APIs de Windows de primeira parte (Windows Runtime APIs em namespaces Windows). Esses cabeçalhos estão dentro da pasta %WindowsSdkDir%Include<WindowsTargetPlatformVersion>\cppwinrt\winrt. A partir do Windows SDK versão 10.0.17763.0 (Windows 10, versão 1809), esses cabeçalhos são gerados para você dentro da pasta $(GeneratedFilesDir) do projeto.

Novamente para compatibilidade, o SDK do Windows também vem com a cppwinrt.exe ferramenta. No entanto, recomendamos que você instale e use, em vez disso, a versão mais recente de cppwinrt.exe, que está incluída no pacote NuGet Microsoft.Windows.CppWinRT. Esse pacote e cppwinrt.exe. são descritos nas seções acima.

Tipos personalizados na projeção C++/WinRT

Em sua programação C++/WinRT, você pode usar recursos de linguagem C++ padrão e tipos de dados C++ Padrão e C++/WinRT, incluindo alguns tipos de dados da Biblioteca Padrão C++. Mas você também estará ciente de alguns tipos de dados personalizados na projeção e poderá optar por usá-los. Por exemplo, usamos winrt::hstring no exemplo de código de início rápido em Introdução ao C++/WinRT.

winrt::com_array é outro tipo que você provavelmente usará em algum momento. Mas é menos provável que você use diretamente um tipo como winrt::array_view. Ou você pode optar por não usá-lo para não ter nenhum código a ser alterado se e quando um tipo equivalente aparecer na Biblioteca Padrão C++.

Aviso

Também há tipos que você poderá ver se estudar de perto os cabeçalhos do namespace Windows C++/WinRT. Um exemplo é winrt::param::hstring, mas também há exemplos de coleções. Elas existem apenas para otimizar a associação de parâmetros de entrada e geram grandes melhorias de desempenho e fazem com que a maioria dos padrões de chamada "apenas funcione" para tipos e contêineres C++ padrão relacionados. Esses tipos só são usados pela projeção nos casos em que eles adicionam mais valor. Eles são altamente otimizados e não são para uso geral; não fique tentado a usá-los por conta própria. Também não deve usar nada do winrt::impl namespace, pois são tipos de implementação e, portanto, sujeitos a alterações. Você deve continuar a usar tipos padrão ou tipos do namespace winrt.

Veja também Passando parâmetros pela fronteira da ABI.

APIs importantes