diff --git a/Example/Pods/Pods.xcodeproj/project.pbxproj b/Example/Pods/Pods.xcodeproj/project.pbxproj index b34c80e..8bc1bba 100644 --- a/Example/Pods/Pods.xcodeproj/project.pbxproj +++ b/Example/Pods/Pods.xcodeproj/project.pbxproj @@ -43,14 +43,14 @@ 006ACEA189C994CD829CEA4104BDFF83 /* SwiftVideoGenerator.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = SwiftVideoGenerator.xcconfig; sourceTree = ""; }; 06ACC0F69337F4768E18709F44606C0E /* Pods-SwiftVideoGenerator_Example-acknowledgements.plist */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.plist.xml; path = "Pods-SwiftVideoGenerator_Example-acknowledgements.plist"; sourceTree = ""; }; 0A3302C62684FF52EE57F2CE921A70DC /* Pods-SwiftVideoGenerator_Tests-acknowledgements.markdown */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text; path = "Pods-SwiftVideoGenerator_Tests-acknowledgements.markdown"; sourceTree = ""; }; - 0D0565DB0158266FFB8EA93A988CF0D9 /* SwiftVideoGenerator.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; name = SwiftVideoGenerator.framework; path = SwiftVideoGenerator.framework; sourceTree = BUILT_PRODUCTS_DIR; }; + 0D0565DB0158266FFB8EA93A988CF0D9 /* SwiftVideoGenerator.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = SwiftVideoGenerator.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 0E798788BDFB9BE0F29AC151F3ED34BF /* Pods-SwiftVideoGenerator_Tests-frameworks.sh */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.script.sh; path = "Pods-SwiftVideoGenerator_Tests-frameworks.sh"; sourceTree = ""; }; 1484AB9624D25C61CDCA3E39FDA691B6 /* Pods-SwiftVideoGenerator_Example-frameworks.sh */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.script.sh; path = "Pods-SwiftVideoGenerator_Example-frameworks.sh"; sourceTree = ""; }; 1DE77ECD91B41A0F49965F06AE42B218 /* Pods-SwiftVideoGenerator_Example-dummy.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; path = "Pods-SwiftVideoGenerator_Example-dummy.m"; sourceTree = ""; }; - 277115F4E28D8E05D1E16D5273DDCE35 /* Pods_SwiftVideoGenerator_Tests.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; name = Pods_SwiftVideoGenerator_Tests.framework; path = "Pods-SwiftVideoGenerator_Tests.framework"; sourceTree = BUILT_PRODUCTS_DIR; }; + 277115F4E28D8E05D1E16D5273DDCE35 /* Pods_SwiftVideoGenerator_Tests.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_SwiftVideoGenerator_Tests.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 30FF659A1FE6114A9283C695DF397538 /* Info.plist */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 45858AED706767FAD3BADC5A9F24B74D /* Info.plist */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; - 52796856D2D6A3AA56606F6571535C80 /* SwiftVideoGenerator.podspec */ = {isa = PBXFileReference; explicitFileType = text.script.ruby; includeInIndex = 1; lastKnownFileType = text; path = SwiftVideoGenerator.podspec; sourceTree = ""; xcLanguageSpecificationIdentifier = xcode.lang.ruby; }; + 52796856D2D6A3AA56606F6571535C80 /* SwiftVideoGenerator.podspec */ = {isa = PBXFileReference; explicitFileType = text.script.ruby; includeInIndex = 1; path = SwiftVideoGenerator.podspec; sourceTree = ""; xcLanguageSpecificationIdentifier = xcode.lang.ruby; }; 6604A7D69453B4569E4E4827FB9155A9 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS10.3.sdk/System/Library/Frameworks/Foundation.framework; sourceTree = DEVELOPER_DIR; }; 67D75CB3C03EF3928F25179DFEAEDE32 /* Info.plist */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 6C61B914018CED7BA6ABA859D5E2D432 /* Pods-SwiftVideoGenerator_Example-acknowledgements.markdown */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text; path = "Pods-SwiftVideoGenerator_Example-acknowledgements.markdown"; sourceTree = ""; }; @@ -62,21 +62,21 @@ 8781CFCD878CAAE3ECFA0D94437B6D6B /* Pods-SwiftVideoGenerator_Example.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = "Pods-SwiftVideoGenerator_Example.debug.xcconfig"; sourceTree = ""; }; 894FD64BF347EFEB45E92AEE12E3C537 /* Pods-SwiftVideoGenerator_Tests.release.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = "Pods-SwiftVideoGenerator_Tests.release.xcconfig"; sourceTree = ""; }; 925DAFE8CEB90A9A316FCADEF23689F2 /* Pods-SwiftVideoGenerator_Tests-umbrella.h */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.h; path = "Pods-SwiftVideoGenerator_Tests-umbrella.h"; sourceTree = ""; }; - 93A4A3777CF96A4AAC1D13BA6DCCEA73 /* Podfile */ = {isa = PBXFileReference; explicitFileType = text.script.ruby; includeInIndex = 1; lastKnownFileType = text; name = Podfile; path = ../Podfile; sourceTree = SOURCE_ROOT; xcLanguageSpecificationIdentifier = xcode.lang.ruby; }; + 93A4A3777CF96A4AAC1D13BA6DCCEA73 /* Podfile */ = {isa = PBXFileReference; explicitFileType = text.script.ruby; includeInIndex = 1; name = Podfile; path = ../Podfile; sourceTree = SOURCE_ROOT; xcLanguageSpecificationIdentifier = xcode.lang.ruby; }; 943E3985FF4DF8721F607E168E39EE2C /* Pods-SwiftVideoGenerator_Example-resources.sh */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.script.sh; path = "Pods-SwiftVideoGenerator_Example-resources.sh"; sourceTree = ""; }; 98BE05E74096865E079E7D74147FF715 /* Pods-SwiftVideoGenerator_Tests-dummy.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; path = "Pods-SwiftVideoGenerator_Tests-dummy.m"; sourceTree = ""; }; 998A00F7CE6F15E3B2733D6104A29195 /* VideoGeneratorError.swift */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.swift; path = VideoGeneratorError.swift; sourceTree = ""; }; A5BED199322B1FEA5CF9FD9B020A6048 /* Pods-SwiftVideoGenerator_Tests.modulemap */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.module; path = "Pods-SwiftVideoGenerator_Tests.modulemap"; sourceTree = ""; }; AEF974144DD0B1E7C4B52832CDE32F6A /* SwiftVideoGenerator.modulemap */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.module; path = SwiftVideoGenerator.modulemap; sourceTree = ""; }; B0D5515FEE7FB9D47DBC7BFB68011C6C /* Pods-SwiftVideoGenerator_Example.modulemap */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.module; path = "Pods-SwiftVideoGenerator_Example.modulemap"; sourceTree = ""; }; - B415E5DA1EC95D63A32007152108F514 /* LICENSE */ = {isa = PBXFileReference; includeInIndex = 1; path = LICENSE; sourceTree = ""; }; + B415E5DA1EC95D63A32007152108F514 /* LICENSE */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text; path = LICENSE; sourceTree = ""; }; C9934D26A2888DC93EBAE033659E667E /* SwiftVideoGenerator-umbrella.h */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.h; path = "SwiftVideoGenerator-umbrella.h"; sourceTree = ""; }; CDAC6596A3AAF33C62730BF2A9117DB6 /* Pods-SwiftVideoGenerator_Tests.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; path = "Pods-SwiftVideoGenerator_Tests.debug.xcconfig"; sourceTree = ""; }; - CEA88D5E2F6796AA0C44FD32864611C5 /* Pods_SwiftVideoGenerator_Example.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; name = Pods_SwiftVideoGenerator_Example.framework; path = "Pods-SwiftVideoGenerator_Example.framework"; sourceTree = BUILT_PRODUCTS_DIR; }; + CEA88D5E2F6796AA0C44FD32864611C5 /* Pods_SwiftVideoGenerator_Example.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Pods_SwiftVideoGenerator_Example.framework; sourceTree = BUILT_PRODUCTS_DIR; }; D1769BF43420CD44F192693D731B4B62 /* SwiftVideoGenerator-dummy.m */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.c.objc; path = "SwiftVideoGenerator-dummy.m"; sourceTree = ""; }; D37291F249B93EA58768F079C6BF130A /* AVAssetExtension.swift */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.swift; path = AVAssetExtension.swift; sourceTree = ""; }; DC4C5D9AA1341DC769A154A523F3E97A /* ImageExtension.swift */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.swift; path = ImageExtension.swift; sourceTree = ""; }; - FA84AAB9F414B486C0045F337986DA98 /* README.md */ = {isa = PBXFileReference; includeInIndex = 1; path = README.md; sourceTree = ""; }; + FA84AAB9F414B486C0045F337986DA98 /* README.md */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = net.daringfireball.markdown; path = README.md; sourceTree = ""; }; FFD3C8E0B3BFD1A47472FA09C21497E9 /* VideoGenerator.swift */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = sourcecode.swift; name = VideoGenerator.swift; path = SwiftVideoGenerator/Classes/VideoGenerator.swift; sourceTree = ""; }; /* End PBXFileReference section */ @@ -344,14 +344,15 @@ isa = PBXProject; attributes = { LastSwiftUpdateCheck = 0930; - LastUpgradeCheck = 0930; + LastUpgradeCheck = 1030; }; buildConfigurationList = 2D8E8EC45A3A1A1D94AE762CB5028504 /* Build configuration list for PBXProject "Pods" */; compatibilityVersion = "Xcode 3.2"; - developmentRegion = English; + developmentRegion = en; hasScannedForEncodings = 0; knownRegions = ( en, + Base, ); mainGroup = 7DB346D0F39D3F0E887471402A8071AB; productRefGroup = D6A0FA01CD2FB7D268FD276E70EEE5B2 /* Products */; @@ -416,6 +417,7 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; CLANG_ANALYZER_NONNULL = YES; CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; @@ -479,6 +481,7 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = NO; + CLANG_ANALYZER_LOCALIZABILITY_NONLOCALIZED = YES; CLANG_ANALYZER_NONNULL = YES; CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; @@ -529,6 +532,7 @@ MTL_ENABLE_DEBUG_INFO = NO; PRODUCT_NAME = "$(TARGET_NAME)"; STRIP_INSTALLED_PRODUCT = NO; + SWIFT_COMPILATION_MODE = wholemodule; SYMROOT = "${SRCROOT}/../build"; }; name = Release; diff --git a/Example/SwiftVideoGenerator.xcodeproj/xcshareddata/xcschemes/SwiftVideoGenerator-Example.xcscheme b/Example/SwiftVideoGenerator.xcodeproj/xcshareddata/xcschemes/SwiftVideoGenerator-Example.xcscheme index 09fb3f2..bc213a7 100644 --- a/Example/SwiftVideoGenerator.xcodeproj/xcshareddata/xcschemes/SwiftVideoGenerator-Example.xcscheme +++ b/Example/SwiftVideoGenerator.xcodeproj/xcshareddata/xcschemes/SwiftVideoGenerator-Example.xcscheme @@ -1,6 +1,6 @@ 'MIT', :file => 'LICENSE' } diff --git a/SwiftVideoGenerator/Classes/VideoGenerator.swift b/SwiftVideoGenerator/Classes/VideoGenerator.swift index a1a3f06..0a261cc 100644 --- a/SwiftVideoGenerator/Classes/VideoGenerator.swift +++ b/SwiftVideoGenerator/Classes/VideoGenerator.swift @@ -38,25 +38,28 @@ public class VideoGenerator: NSObject { // MARK: --------------------------------------------------------------- Public properties --------------------------------------------------------------- /// public property to set the name of the finished video file - open var fileName = "movie" + public static var fileName = "movie" /// public property to set a multiple type video's background color - open var videoBackgroundColor: UIColor = UIColor.black + public static var videoBackgroundColor: UIColor = UIColor.black + + /// public property to set the AVAssetExportPreset + public static var presetName: String? /// public property to set a width to scale the image to before generating a video (used only with .single type video generation; preferred scale: 800/1200) - open var scaleWidth: CGFloat? + public static var scaleWidth: CGFloat? /// public property to indicate if the images fed into the generator should be resized to appropriate video ratio 1200 x 1920 - open var shouldOptimiseImageForVideo: Bool = true + public static var shouldOptimiseImageForVideo: Bool = true /// public property to set the maximum length of a video - open var maxVideoLengthInSeconds: Double? + public static var maxVideoLengthInSeconds: Double? /// public property to set a width to which to resize the images for multiple video generation. Default value is 800 - open var videoImageWidthForMultipleVideoGeneration = 800 + public static var videoImageWidthForMultipleVideoGeneration = 800 /// public property to set the video duration when there is no audio - open var videoDurationInSeconds: Double = 0 { + public static var videoDurationInSeconds: Double = 0 { didSet { videoDurationInSeconds = Double(CMTime(seconds: videoDurationInSeconds, preferredTimescale: 1).seconds) } @@ -205,7 +208,7 @@ public class VideoGenerator: NSObject { // after all images are appended the writting shoul be marked as finished videoWriterInput.markAsFinished() - if let _maxLength = self?.maxVideoLengthInSeconds { + if let _maxLength = VideoGenerator.maxVideoLengthInSeconds { videoWriter.endSession(atSourceTime: CMTime(seconds: _maxLength, preferredTimescale: 1)) } @@ -213,7 +216,7 @@ public class VideoGenerator: NSObject { videoWriter.finishWriting { () -> Void in if self?.audioURLs.isEmpty == true { if let documentsPath = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).first { - let newPath = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(self?.fileName ?? "").m4v") + let newPath = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(VideoGenerator.fileName).m4v") self?.deleteFile(pathURL: newPath, completion: { try FileManager.default.moveItem(at: videoOutputURL, to: newPath) }) @@ -258,10 +261,9 @@ public class VideoGenerator: NSObject { /// - fileName: the name of the finished merged video file /// - success: success block - returns the finished video url path /// - failure: failure block - returns the error that caused the failure - open class func mergeMovies(videoURLs: [URL], andFileName fileName: String, success: @escaping ((URL) -> Void), failure: @escaping ((Error) -> Void)) { + open class func mergeMovies(videoURLs: [URL], success: @escaping ((URL) -> Void), failure: @escaping ((Error) -> Void)) { let acceptableVideoExtensions = ["mov", "mp4", "m4v"] let _videoURLs = videoURLs.filter({ !$0.absoluteString.contains(".DS_Store") && acceptableVideoExtensions.contains($0.pathExtension.lowercased()) }) - let _fileName = fileName == "" ? "mergedMovie" : fileName /// guard against missing URLs guard !_videoURLs.isEmpty else { @@ -282,7 +284,7 @@ public class VideoGenerator: NSObject { if let documentsPath = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).first { /// create a path to the video file - completeMoviePath = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(_fileName).m4v") + completeMoviePath = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(VideoGenerator.fileName).m4v") if let completeMoviePath = completeMoviePath { if FileManager.default.fileExists(atPath: completeMoviePath.path) { @@ -331,7 +333,7 @@ public class VideoGenerator: NSObject { } /// try to start an export session and set the path and file type - if let exportSession = AVAssetExportSession(asset: composition, presetName: AVAssetExportPresetHighestQuality) { + if let exportSession = AVAssetExportSession(asset: composition, presetName: presetName ?? AVAssetExportPresetHighestQuality) { exportSession.outputURL = completeMoviePath exportSession.outputFileType = AVFileType.mp4 exportSession.shouldOptimizeForNetworkUse = true @@ -379,10 +381,8 @@ public class VideoGenerator: NSObject { /// - sound: indicates if the sound should be kept and reversed as well /// - success: completion block on success - returns the audio URL /// - failure: completion block on failure - returns the error that caused the failure - open func reverseVideo(fromVideo videoURL: URL, andFileName fileName: String, success: @escaping ((URL) -> Void), failure: @escaping ((Error) -> Void)) { - self.fileName = fileName - - self.reverseVideoClip(videoURL: videoURL, andFileName: fileName, success: { (reversedVideo) in + open func reverseVideo(fromVideo videoURL: URL, success: @escaping ((URL) -> Void), failure: @escaping ((Error) -> Void)) { + self.reverseVideoClip(videoURL: videoURL, andFileName: VideoGenerator.fileName, success: { (reversedVideo) in success(reversedVideo) }, failure: { (error) in failure(error) @@ -410,7 +410,7 @@ public class VideoGenerator: NSObject { } if let documentsPath = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).first { - let outputURL = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(fileName).m4v") + let outputURL = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(VideoGenerator.fileName).m4v") let sourceAsset = AVURLAsset(url: videoURL, options: nil) let length = CMTime(seconds: sourceAsset.duration.seconds, preferredTimescale: sourceAsset.duration.timescale) @@ -422,7 +422,7 @@ public class VideoGenerator: NSObject { print(error.localizedDescription) } - if let exportSession = AVAssetExportSession(asset: sourceAsset, presetName: AVAssetExportPresetHighestQuality) { + if let exportSession = AVAssetExportSession(asset: sourceAsset, presetName: VideoGenerator.presetName ?? AVAssetExportPresetHighestQuality) { exportSession.outputURL = outputURL exportSession.outputFileType = AVFileType.mp4 exportSession.shouldOptimizeForNetworkUse = true @@ -498,7 +498,7 @@ public class VideoGenerator: NSObject { mutableVideoComposition.renderSize = CGSize(width: 1280, height: 720) if let documentsPath = NSSearchPathForDirectoriesInDomains(.documentDirectory, .userDomainMask, true).first { - let outputURL = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(fileName).m4v") + let outputURL = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(VideoGenerator.fileName).m4v") do { if FileManager.default.fileExists(atPath: outputURL.path) { @@ -508,7 +508,7 @@ public class VideoGenerator: NSObject { print(error.localizedDescription) } - if let exportSession = AVAssetExportSession(asset: mixComposition, presetName: AVAssetExportPresetHighestQuality) { + if let exportSession = AVAssetExportSession(asset: mixComposition, presetName: VideoGenerator.presetName ?? AVAssetExportPresetHighestQuality) { exportSession.outputURL = outputURL exportSession.outputFileType = AVFileType.mp4 exportSession.shouldOptimizeForNetworkUse = true @@ -567,14 +567,14 @@ public class VideoGenerator: NSObject { audioURLs = _audios if self.type == .single { - if let _image = self.shouldOptimiseImageForVideo ? _images.first?.resizeImageToVideoSize() : _images.first { + if let _image = VideoGenerator.shouldOptimiseImageForVideo ? _images.first?.resizeImageToVideoSize() : _images.first { self.images = [UIImage](repeating: _image, count: 2) } } else { for _image in _images { autoreleasepool { - if let imageData = _image.scaleImageToSize(newSize: CGSize(width: videoImageWidthForMultipleVideoGeneration, height: videoImageWidthForMultipleVideoGeneration))?.pngData() { + if let imageData = _image.scaleImageToSize(newSize: CGSize(width: VideoGenerator.videoImageWidthForMultipleVideoGeneration, height: VideoGenerator.videoImageWidthForMultipleVideoGeneration))?.pngData() { datasImages.append(imageData) } } @@ -618,7 +618,7 @@ public class VideoGenerator: NSObject { /// calculate the full video duration for audio in audioAssets { - if let _maxLength = maxVideoLengthInSeconds { + if let _maxLength = VideoGenerator.maxVideoLengthInSeconds { _duration += round(Double(CMTimeGetSeconds(audio.duration))) if _duration < _maxLength { @@ -636,13 +636,13 @@ public class VideoGenerator: NSObject { } let minVideoDuration = Double(CMTime(seconds: minSingleVideoDuration, preferredTimescale: 1).seconds) - duration = max((audioURLs.isEmpty ? videoDurationInSeconds : _duration), minVideoDuration) + duration = max((audioURLs.isEmpty ? VideoGenerator.videoDurationInSeconds : _duration), minVideoDuration) if audioURLs.isEmpty { audioDurations = [Double](repeating: duration / Double(images.count), count: images.count) } - if let _scaleWidth = scaleWidth { + if let _scaleWidth = VideoGenerator.scaleWidth { images = images.compactMap({ $0.scaleImageToSize(newSize: CGSize(width: _scaleWidth, height: _scaleWidth)) }) } } @@ -715,9 +715,9 @@ public class VideoGenerator: NSObject { let audioDuration = CMTime(seconds: self?.audioDurations[index] ?? 0.0, preferredTimescale: 1) let audioAsset = AVURLAsset(url: audioUrl) - let audioTimeRange = CMTimeRange(start: CMTime.zero, duration: self?.maxVideoLengthInSeconds != nil ? audioDuration : audioAsset.duration) + let audioTimeRange = CMTimeRange(start: CMTime.zero, duration: VideoGenerator.maxVideoLengthInSeconds != nil ? audioDuration : audioAsset.duration) - let shouldAddAudioTrack = self?.maxVideoLengthInSeconds != nil ? audioDuration.seconds > 0 : true + let shouldAddAudioTrack = VideoGenerator.maxVideoLengthInSeconds != nil ? audioDuration.seconds > 0 : true if shouldAddAudioTrack { if let audioTrack = audioAsset.tracks(withMediaType: .audio).first { @@ -729,7 +729,7 @@ public class VideoGenerator: NSObject { } } - duration = duration + (self?.maxVideoLengthInSeconds != nil ? audioDuration : audioAsset.duration) + duration = duration + (VideoGenerator.maxVideoLengthInSeconds != nil ? audioDuration : audioAsset.duration) } /// check if the documents folder is available @@ -737,9 +737,9 @@ public class VideoGenerator: NSObject { self?.getTempVideoFileUrl { (_) in } /// create a path to the video file - let videoOutputURL = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(self?.fileName ?? "").m4v") + let videoOutputURL = URL(fileURLWithPath: documentsPath).appendingPathComponent("\(VideoGenerator.fileName).m4v") self?.deleteFile(pathURL: videoOutputURL) { - if let exportSession = AVAssetExportSession(asset: mixComposition, presetName: AVAssetExportPresetHighestQuality) { + if let exportSession = AVAssetExportSession(asset: mixComposition, presetName: VideoGenerator.presetName ?? AVAssetExportPresetHighestQuality) { exportSession.outputURL = videoOutputURL exportSession.outputFileType = AVFileType.mp4 exportSession.shouldOptimizeForNetworkUse = true @@ -1237,7 +1237,7 @@ public class VideoGenerator: NSObject { context.clear(CGRect(x: 0.0, y: 0.0, width: imageWidth, height: imageHeight)) // set the context's background color - context.setFillColor(type == .single ? UIColor.black.cgColor : videoBackgroundColor.cgColor) + context.setFillColor(type == .single ? UIColor.black.cgColor : VideoGenerator.videoBackgroundColor.cgColor) context.fill(CGRect(x: 0.0, y: 0.0, width: CGFloat(context.width), height: CGFloat(context.height))) context.concatenate(.identity)