Swift生成GIF时如何调整单帧延迟时长?
解决GIF帧延迟不生效的问题
你的核心问题是帧延迟的属性结构嵌套错误,kCGImagePropertyGIFDelayTime需要包裹在kCGImagePropertyGIFDictionary的子字典中,而不是直接作为顶层属性,这才导致设置的延迟未被正确识别。
修正后的代码
修改你设置frameProperties的部分,调整为正确的嵌套结构:
public func generateGifFromImages(imagesArray: [CGImage], repeatCount: Int = 0, frameDelay: TimeInterval, targetSize: CGSize, destinationURL: URL, progressHandler: @escaping (Float) -> (), callback: @escaping (_ data: Data?, _ error: NSError?) -> ()) { DispatchQueue.global(qos: .background).async { if let imageDestination = CGImageDestinationCreateWithURL(destinationURL as CFURL, kUTTypeGIF, imagesArray.count, nil) { let gifProperties = [kCGImagePropertyGIFDictionary as String: [kCGImagePropertyGIFLoopCount as String: repeatCount]] // Calculate total progress steps let totalSteps = imagesArray.count var currentStep = 0 for image in imagesArray { // Resize image while maintaining aspect ratio guard let resizedImage = self.resize(image: image, targetSize: targetSize) else { callback(nil, self.errorFromString("Couldn't resize image")) return } // 修正:将延迟属性嵌套到GIF子字典中 let frameProperties: [String: Any] = [ kCGImagePropertyGIFDictionary as String: [ kCGImagePropertyGIFDelayTime as String: frameDelay ] ] // Add the resized image to the GIF CGImageDestinationAddImage(imageDestination, resizedImage, frameProperties as CFDictionary ) // Update progress currentStep += 1 let progress = Float(currentStep) / Float(totalSteps) progressHandler(progress) } CGImageDestinationSetProperties(imageDestination, gifProperties as CFDictionary) if CGImageDestinationFinalize(imageDestination) { do { let data = try Data(contentsOf: destinationURL) callback(data, nil) } catch { callback(nil, error as NSError) } } else { callback(nil, self.errorFromString("Couldn't create the final image")) } } } }
额外注意事项
- 确保传入的
frameDelay以秒为单位,比如要每帧显示1秒,直接传入1.0即可。 - 部分GIF播放器会对最小延迟做限制(比如至少0.1秒),但1秒的延迟完全在有效范围内,不会被播放器截断。
- 检查
resize方法是否正确处理图片尺寸,避免因图片异常导致的播放问题。
内容的提问来源于stack exchange,提问作者Amit K.
相关产品推荐
相关产品推荐

