You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Xamarin.iOS中显示Azure通知中心推送的带图通知(无服务扩展)

Displaying Image Attachments in Xamarin.iOS Foreground Notifications (DidReceiveRemoteNotification)

I get it, the official docs can feel pretty dense when you're trying to add images to notifications without using a service extension. Let's break this down and modify your existing DidReceiveRemoteNotification method to show notifications with images when your app is in the foreground.

Key Things to Know

  • When your app is active (foreground), iOS doesn't automatically show a notification banner—you have to create and present the notification manually using UNUserNotificationCenter.
  • Notification attachments require local files, so we'll need to download the image from your backend's URL to a temporary local file first.

Modified Code Example

Here's how to update your method to handle image attachments:

using System;
using System.IO;
using System.Net.Http;
using System.Threading.Tasks;
using Foundation;
using UIKit;
using UserNotifications;

// Ensure your delegate inherits from UNUserNotificationCenterDelegate
public class YourNotificationDelegate : UNUserNotificationCenterDelegate
{
    public override async void DidReceiveRemoteNotification(UIApplication application, NSDictionary userInfo, Action completionHandler)
    {
        NSDictionary aps = userInfo.ObjectForKey(new NSString("aps")) as NSDictionary;
        NSDictionary detailedInfo = aps?.ObjectForKey(new NSString("alert")) as NSDictionary;
        NSDictionary custom = userInfo.ObjectForKey(new NSString("custom")) as NSDictionary;

        // Define your payload keys
        var messageTitleKey = new NSString("title");
        var messageBodyKey = new NSString("body");
        var orderIdKey = new NSString("orderid");
        var pageToNavigateKey = new NSString("page");
        var notificationDbIdKey = new NSString("notificationDbId");
        var imageUrlKey = new NSString("image_url"); // Add this key for your image URL in the custom payload

        LinkNavigation linkNavigation = new LinkNavigation();
        string message = null, orderId = null, page = null, notificationId = null, imageUrl = null;

        // Extract existing payload data
        if (detailedInfo != null && detailedInfo.ContainsKey(messageBodyKey))
        {
            message = (detailedInfo[messageBodyKey] as NSString).ToString();
        }

        if (custom != null)
        {
            if (custom.ContainsKey(orderIdKey))
            {
                orderId = (custom[orderIdKey] as NSString).ToString();
                linkNavigation.OrderId = !string.IsNullOrEmpty(orderId) ? orderId : null;
            }

            if (custom.ContainsKey(pageToNavigateKey))
            {
                page = (custom[pageToNavigateKey] as NSString).ToString();
                if (!string.IsNullOrEmpty(page))
                {
                    linkNavigation.Pagename = Convert.ToInt16(page);
                }
            }

            if (custom.ContainsKey(notificationDbIdKey))
            {
                notificationId = (custom[notificationDbIdKey] as NSString).ToString();
                if (!string.IsNullOrEmpty(notificationId))
                {
                    NotificationReadUnread(long.Parse(notificationId));
                }
            }

            // Extract the image URL from your custom payload
            if (custom.ContainsKey(imageUrlKey))
            {
                imageUrl = (custom[imageUrlKey] as NSString).ToString();
            }
        }

        // Handle app navigation as before
        if (!string.IsNullOrEmpty(orderId) || !string.IsNullOrEmpty(page))
        {
            LoadApplication(new App(linkNavigation));
        }

        // Show notification with image if we have a valid URL and app is active
        if (!string.IsNullOrEmpty(imageUrl) && application.ApplicationState == UIApplicationState.Active)
        {
            try
            {
                // Step 1: Download the image from the URL
                using (var httpClient = new HttpClient())
                {
                    byte[] imageData = await httpClient.GetByteArrayAsync(imageUrl);

                    // Step 2: Save image to a temporary directory (required for notifications)
                    string tempDir = Path.Combine(NSTemporaryDirectory(), "NotificationImages");
                    Directory.CreateDirectory(tempDir);
                    string filePath = Path.Combine(tempDir, $"notification_img_{Guid.NewGuid()}.jpg");
                    File.WriteAllBytes(filePath, imageData);

                    // Step 3: Create a UNNotificationAttachment from the local file
                    var attachmentOptions = new UNNotificationAttachmentOptions();
                    UNNotificationAttachment attachment = await UNNotificationAttachment.CreateAsync(
                        identifier: "image_attachment",
                        url: NSUrl.FromFilename(filePath),
                        options: attachmentOptions);

                    // Step 4: Build the notification content
                    var notificationContent = new UNMutableNotificationContent();
                    notificationContent.Title = detailedInfo?[messageTitleKey]?.ToString() ?? "New Notification";
                    notificationContent.Body = message ?? "You have a new message";
                    notificationContent.Attachments = new[] { attachment };

                    // Step 5: Create and present the notification
                    var request = UNNotificationRequest.FromIdentifier(
                        identifier: $"notification_{Guid.NewGuid()}",
                        content: notificationContent,
                        trigger: null); // Trigger immediately

                    await UNUserNotificationCenter.Current.AddNotificationRequestAsync(request);
                }
            }
            catch (Exception ex)
            {
                // Log any errors (e.g., failed download, invalid image format)
                Console.WriteLine($"Error showing image notification: {ex.Message}");
            }
        }

        // Don't forget to call the completion handler
        completionHandler();
    }

    // Your existing NotificationReadUnread method and other helper code here
    private void NotificationReadUnread(long notificationId)
    {
        // Your implementation
    }
}

Important Notes

  • Payload Structure: Make sure your backend sends the image URL in the custom section of the payload under the key image_url (adjust the key name in the code if your backend uses a different one).
  • Permissions: Ensure you've requested user permission for notifications in your app startup code:
    var center = UNUserNotificationCenter.Current;
    await center.RequestAuthorizationAsync(UNAuthorizationOptions.Alert | UNAuthorizationOptions.Sound | UNAuthorizationOptions.Badge);
    
  • Image Requirements: The image should be in a supported format (JPG, PNG, GIF), and the URL should be publicly accessible. If it's a private URL, modify the HttpClient call to include authentication headers.
  • Temporary Files: We're using the app's temporary directory to store the image—iOS will clean this up automatically, so no need to worry about leftover files.

内容的提问来源于stack exchange,提问作者Sneha Das

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.07 21:47:49