无法生成随后共享的图像

问题描述 投票:0回答:1

我正在 swiftUI 中编码,我正在尝试创建一个按钮,该按钮首先生成新图像,然后打开一个可以共享新图像的 ShareSheet。但是,对于下面的代码,仅共享描述。有人可以帮我解决问题吗?

import SwiftUI
import UIKit


struct ShareSheetViewTESTER: UIViewControllerRepresentable {
    var imageToShare: UIImage
    var descriptionToShare: String

    
    var itemsToShare: [Any] {
        return [imageToShare, descriptionToShare]
    }

    func makeUIViewController(context: Context) -> UIActivityViewController {
        let activityVC = UIActivityViewController(activityItems: itemsToShare, applicationActivities: nil)
        return activityVC
    }

    func updateUIViewController(_ uiViewController: UIActivityViewController, context: Context) {
        
    }
}

struct FriendsView: View {
    @State private var showShareSheet = false
    @State private var image = UIImage(named: "Kort")!
    @State private var description = "Some text here"
    @State private var generatedImage: UIImage?

    var body: some View {
        VStack {
            Button(action: {
                generateImage()
                self.showShareSheet = true
            }) {
                Image(systemName: "square.and.arrow.up")
                    .frame(width: 25, height: 25)
            }
            .sheet(isPresented: $showShareSheet) {
                ShareSheetViewTESTER(imageToShare: generatedImage ?? self.image, descriptionToShare: self.description)
                
            }
        }
    }
    func generateImage() {
        if let imageFromBundle = UIImage(named: "Kort") {
            let textToOverlay = "Text to be put on the photo"
            
            let imageRenderer = UIGraphicsImageRenderer(size: imageFromBundle.size)
            let generatedImage = imageRenderer.image { context in
                imageFromBundle.draw(at: .zero)
                
                let paragraphStyle = NSMutableParagraphStyle()
                paragraphStyle.alignment = .center
                paragraphStyle.lineBreakMode = .byWordWrapping
                
                let attributes: [NSAttributedString.Key: Any] = [
                    .font: UIFont.systemFont(ofSize: 20),
                    .foregroundColor: UIColor.black,
                    .paragraphStyle: paragraphStyle
                ]
                
                let textNSString = textToOverlay as NSString
                let textSize = textNSString.boundingRect(with: CGSize(width: imageFromBundle.size.width, height: .greatestFiniteMagnitude), options: .usesLineFragmentOrigin, attributes: attributes, context: nil).size
                
                let textRect = CGRect(x: 0, y: 170, width: imageFromBundle.size.width, height: textSize.height)
                
                textNSString.draw(in: textRect, withAttributes: attributes)
            }
            
            self.generatedImage = generatedImage
            
        }
    }
}

struct FriendsView_Previews: PreviewProvider {
    static var previews: some View {
        FriendsView()
    }
}

我尝试了其他几种解决方案,但没有任何效果。如果有人能在这里帮助我,我会非常高兴。

swift swiftui uiimage swiftui-sharelink
1个回答
0
投票

图像和描述似乎已正确共享(例如,在 SwiftUI 预览中保存到文件时),但共享表中的预览不包含共享图像。此问题的出现是由于

UIActivityViewController
管理共享项目的呈现方式所致。为了保证共享内容在共享表预览中准确显示,可以实现一个符合
UIActivityItemSource
协议的自定义类。这种方法增强了对共享内容及其元数据的控制。

这是一个完善的解决方案:

import UIKit
import LinkPresentation

// Custom class representing the item to be shared
final class ActivityItem: NSObject {
    let name: String
    let image: UIImage

    init(name: String, image: UIImage) {
        self.name = name
        self.image = image
    }
}

// Conforming to UIActivityItemSource for customized sharing
extension ActivityItem: UIActivityItemSource {
    func activityViewControllerPlaceholderItem(_ activityViewController: UIActivityViewController) -> Any {
        return image
    }

    func activityViewController(_ activityViewController: UIActivityViewController, itemForActivityType activityType: UIActivity.ActivityType?) -> Any? {
        return image
    }

    // Providing metadata for link presentation
    func activityViewControllerLinkMetadata(_ activityViewController: UIActivityViewController) -> LPLinkMetadata? {
        let metaData = LPLinkMetadata()
        metaData.title = name
        metaData.imageProvider = NSItemProvider(object: image)
        return metaData
    }
}

调整

itemsToShare
中的
ShareSheetViewTESTER
属性以包含
ActivityItem
的实例:

var itemsToShare: [Any] {
   [ActivityItem(name: descriptionToShare, image: imageToShare), descriptionToShare]
}

此修改可确保

UIActivityViewController
接收的图像格式能够正确处理以在共享表中共享和预览,同时保持在文件保存场景中观察到的正确共享功能。

© www.soinside.com 2019 - 2024. All rights reserved.