Partilhar via


Notificações de aplicativos da migração UWP para WinUI 3

A única diferença ao migrar o código de notificação da app do UWP para o WinUI é na gestão da ativação das notificações. O envio e o gerenciamento de notificações de aplicativos permanecem exatamente os mesmos.

Note

O termo "notificação de brinde" será substituído por "notificação do aplicativo". Ambos os termos se referem ao mesmo recurso do Windows, mas com o tempo eliminaremos gradualmente o uso de "toast notification" na documentação.

Note

Algumas informações estão relacionadas ao produto pré-lançado, que pode ser substancialmente modificado antes de ser lançado comercialmente. A Microsoft não oferece garantias, expressas ou implícitas, em relação às informações fornecidas aqui.

Diferenças de ativação

Category UWP WinUI
Ponto de entrada de ativação em primeiro plano O método OnActivated dentro de App.xaml.cs é chamado OnLaunched método dentro App.xaml.cs é chamado.
Ponto de entrada de ativação em segundo plano Tratada separadamente como uma tarefa em segundo plano O mesmo que a ativação em primeiro plano. OnLaunched método dentro App.xaml.cs é chamado. Use GetActivatedEventArgs para determinar se o aplicativo deve iniciar totalmente ou apenas manipular a tarefa e sair.
Ativação da janela Sua janela é automaticamente trazida para primeiro plano quando ocorre a ativação em primeiro plano Você deve trazer a sua janela para o primeiro plano, caso o deseje.

Migração para aplicativos C#

Etapa 1: Instalar a biblioteca NuGet

Para uma aplicação WinUI, geres a ativação das notificações usando a classe AppNotificationManager . Esta classe é fornecida pelo pacote NuGet Microsoft.WindowsAppSDK, que está incluído por padrão nos templates de projeto do Visual Studio para WinUI.

Etapa 2: atualizar seu manifesto

No seu Package.appxmanifest, adicione:

  1. Declaração para xmlns:com
  2. Declaração para xmlns:desktop
  3. No atributo IgnorableNamespaces, com e área de trabalho
  4. desktop:Extensão para windows.toastNotificationActivation de forma a declarar o seu CLSID de ativador de notificação toast (usando um novo GUID à sua escolha).
  5. Apenas MSIX: com:Extension para o ativador COM usando o GUID da etapa #4. Certifique-se de incluir o Arguments="----AppNotificationActivated:" para que você saiba que seu lançamento foi a partir de uma notificação
<!--Add these namespaces-->
<Package
  ...
  xmlns:com="http://schemas.microsoft.com/appx/manifest/com/windows10"
  xmlns:desktop="http://schemas.microsoft.com/appx/manifest/desktop/windows10"
  IgnorableNamespaces="... com desktop">
  ...
  <Applications>
    <Application>
      ...
      <Extensions>

        <!--Specify which CLSID to activate when app notification clicked-->
        <desktop:Extension Category="windows.toastNotificationActivation">
          <desktop:ToastNotificationActivation ToastActivatorCLSID="replaced-with-your-guid-C173E6ADF0C3" /> 
        </desktop:Extension>

        <!--Register COM CLSID LocalServer32 registry key-->
        <com:Extension Category="windows.comServer">
          <com:ComServer>
            <com:ExeServer Executable="YourProject.exe" Arguments="----AppNotificationActivated:" DisplayName="App notification activator">
              <com:Class Id="replaced-with-your-guid-C173E6ADF0C3" DisplayName="App notification activator"/>
            </com:ExeServer>
          </com:ComServer>
        </com:Extension>

      </Extensions>
    </Application>
  </Applications>
 </Package>

Etapa 3: Gerir a ativação

No código de inicialização do seu aplicativo (normalmente App.xaml.cs), atualize seu código usando as seguintes etapas:

  1. No OnLaunched, obtenha a instância padrão da classe AppNotificationManager.
  2. Registre-se para o evento AppNotificationManager.NotificationInvoked .
  3. Chame Microsoft.Windows.AppNotifications.AppNotificationManager.Register para registrar seu aplicativo e receber eventos de notificação. É importante que você chame esse método depois de registrar o manipulador NotificationInvoked .
  4. Refatora o seu código de inicialização/ativação de janela num método auxiliar dedicado LaunchAndBringToForegroundIfNeeded, para que o possas chamar de vários locais.
  5. Crie um método auxiliar de HandleNotification, para que ele possa ser chamado de vários lugares.
  6. Chame AppInstance.GetActivatedEventArgs e verifique a propriedade AppActivationArguments.Kind do objeto retornado para o valor ExtendedActivationKind.AppNotification.
  7. Se o tipo de ativação não for AppNotification , chame o método auxiliar LaunchAndBringToForegroundIfNeeded .
  8. Se o tipo de ativação for AppNotification , converta a propriedade AppActivationArguments.Data para um AppNotificationActivatedEventArgs e passe-a para o HandleNotification método auxiliar.
  9. No seu manipulador ApplicationManager.NotificationInvoked, chame o método auxiliar HandleNotification.
  10. Dentro do seu método auxiliar HandleNotification, certifique-se de enviar para o dispatcher de aplicativo ou janela antes de executar qualquer código relacionado à interface do usuário, como mostrar uma janela ou atualizar a interface do usuário
  11. Migre o seu código UWP OnActivated antigo que manipulava a ativação de notificações da aplicação para o seu novo HandleNotification método auxiliar.

Migraram App.xaml.cs


protected override void OnLaunched(Microsoft.UI.Xaml.LaunchActivatedEventArgs args)
{
    m_window = new MainWindow();

    // To ensure all Notification handling happens in this process instance, register for
    // NotificationInvoked before calling Register(). Without this a new process will
    // be launched to handle the notification.
    AppNotificationManager notificationManager = AppNotificationManager.Default;
    notificationManager.NotificationInvoked += NotificationManager_NotificationInvoked;
    notificationManager.Register();

    var activatedArgs = Microsoft.Windows.AppLifecycle.AppInstance.GetCurrent().GetActivatedEventArgs();
    var activationKind = activatedArgs.Kind;
    if (activationKind != ExtendedActivationKind.AppNotification)
    {
        LaunchAndBringToForegroundIfNeeded();
    } else
    {
        HandleNotification((AppNotificationActivatedEventArgs)activatedArgs.Data);
    }

}

private void LaunchAndBringToForegroundIfNeeded()
{
    if (m_window == null)
    {
        m_window = new MainWindow();
        m_window.Activate();

        // Additionally we show using our helper, since if activated via a app notification, it doesn't
        // activate the window correctly.
        WindowHelper.ShowWindow(m_window);
    }
    else
    {
        WindowHelper.ShowWindow(m_window);
    }
}

private void NotificationManager_NotificationInvoked(AppNotificationManager sender, AppNotificationActivatedEventArgs args)
{
    HandleNotification(args);
}

private void HandleNotification(AppNotificationActivatedEventArgs args)
{
  // Use the dispatcher from the window if present, otherwise the app dispatcher.
  var dispatcherQueue = m_window?.DispatcherQueue ?? DispatcherQueue.GetForCurrentThread();


  dispatcherQueue.TryEnqueue(async delegate
  {
      if (args.Argument.Contains("action"))
      {
          switch (args.Arguments["action"])
          {
              // Send a background message.
              case "sendMessage":
                  string message = args.UserInput["textBox"].ToString();
                  // TODO: Send it.
    
                  // If the UI app isn't open.
                  if (m_window == null)
                  {
                      // Close since we're done.
                      Process.GetCurrentProcess().Kill();
                  }
    
                  break;
    
              // View a message.
              case "viewMessage":
    
                  // Launch/bring window to foreground.
                  LaunchAndBringToForegroundIfNeeded();
    
                  // TODO: Open the message.
                  break;
          }
      }
      else
      {
          Debug.Print("Notification args is null");
      }
  });
}

private static class WindowHelper
{
    [DllImport("user32.dll")]
    private static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);

    [DllImport("user32.dll")]
    [return: MarshalAs(UnmanagedType.Bool)]
    private static extern bool SetForegroundWindow(IntPtr hWnd);

    public static void ShowWindow(Window window)
    {
        // Bring the window to the foreground... first get the window handle...
        var hwnd = WinRT.Interop.WindowNative.GetWindowHandle(window);

        // Restore window if minimized... requires DLL import above
        ShowWindow(hwnd, 0x00000009);

        // And call SetForegroundWindow... requires DLL import above
        SetForegroundWindow(hwnd);
    }
}

Criando conteúdo de notificação de aplicativo

Com Windows App SDK, ainda pode criar conteúdo de notificações de aplicações usando XML bruto, mas também pode criar conteúdo de notificação de aplicações usando a nova API AppNotificationsBuilder que substitui a classe ToastContentBuilder fornecida pelo Windows Community Toolkit. Envie a notificação do aplicativo chamando AppNotificationManager.Show. Não é recomendável misturar APIs do Kit de Ferramentas da Comunidade do Windows e do SDK do Aplicativo.

using Microsoft.Windows.AppNotifications;
using Microsoft.Windows.AppNotifications.Builder;

...

var builder = new AppNotificationBuilder()
    .AddText("Send a message.")
    .AddTextBox("textBox")
    .AddButton(new AppNotificationButton("Send")
        .AddArgument("action", "sendMessage"));

var notificationManager = AppNotificationManager.Default;
notificationManager.Show(builder.BuildNotification());