问题描述
我正在尝试通过视频添加UIView,我使用的是这段代码,该代码来自我在互联网上找到的教学语言(overlay video) 功能代码如下:
func addViewToVideo(fromVideoAt videoURL: URL,withView: UIView,onComplete: @escaping (URL?) -> Void) {
let asset = AVURLAsset(url: videoURL)
let composition = AVMutableComposition()
guard
let compositionTrack = composition.addMutableTrack(
withMediaType: .video,preferredTrackID: kCMPersistentTrackID_Invalid),let assetTrack = asset.tracks(withMediaType: .video).first
else {
print("Something is wrong with the asset.")
onComplete(nil)
return
}
do {
let timeRange = CMTimeRange(start: .zero,duration: asset.duration)
try compositionTrack.insertTimeRange(timeRange,of: assetTrack,at: .zero)
if let audioAssetTrack = asset.tracks(withMediaType: .audio).first,let compositionAudioTrack = composition.addMutableTrack(
withMediaType: .audio,preferredTrackID: kCMPersistentTrackID_Invalid) {
try compositionAudioTrack.insertTimeRange(
timeRange,of: audioAssetTrack,at: .zero)
}
} catch {
print(error)
onComplete(nil)
return
}
compositionTrack.preferredTransform = assetTrack.preferredTransform
let videoSize: CGSize = CGSize(width: assetTrack.naturalSize.height,height: assetTrack.naturalSize.width)
let videoLayer = CALayer()
videoLayer.frame = CGRect(origin: .zero,size: videoSize)
let overlayLayer = CALayer()
overlayLayer.frame = CGRect(origin: .zero,size: videoSize)
addImage(imagePassed: self.upperView.asImage(),to: overlayLayer,videoSize: videoSize)
let outputLayer = CALayer()
outputLayer.frame = CGRect(origin: .zero,size: videoSize)
outputLayer.addSublayer(videoLayer)
outputLayer.addSublayer(overlayLayer)
let videoComposition = AVMutableVideoComposition()
videoComposition.renderSize = videoSize
videoComposition.frameDuration = CMTime(value: 1,timescale: 30)
videoComposition.animationTool = AVVideoCompositionCoreAnimationTool(
postProcessingAsVideoLayer: videoLayer,in: outputLayer)
let instruction = AVMutableVideoCompositionInstruction()
instruction.timeRange = CMTimeRange(
start: .zero,duration: composition.duration)
videoComposition.instructions = [instruction]
let layerInstruction = compositionLayerInstruction(
for: compositionTrack,assetTrack: assetTrack)
instruction.layerInstructions = [layerInstruction]
guard let export = AVAssetExportSession(
asset: composition,presetName: AVAssetExportPresetHighestQuality)
else {
print("Cannot create export session.")
onComplete(nil)
return
}
let videoName = UUID().uuidString
let exportURL = URL(fileURLWithPath: NstemporaryDirectory())
.appendingPathComponent(videoName)
.appendingPathExtension("mov")
export.videoComposition = videoComposition
export.outputFileType = .mov
export.outputURL = exportURL
export.exportAsynchronously {
dispatchQueue.main.async {
switch export.status {
case .completed:
onComplete(exportURL)
default:
print("Something went wrong during export.")
print(export.error ?? "unkNown error")
onComplete(nil)
break
}
}
}
}
private func addImage(imagePassed: UIImage,to layer: CALayer,videoSize: CGSize) {
let image = imagePassed
let imageLayer = CALayer()
let aspect: CGFloat = image.size.width / image.size.height
let width = videoSize.width
let height = width / aspect
imageLayer.frame = CGRect(
x: 0,y: -height * 0.15,width: width,height: height)
imageLayer.contents = image.cgImage
layer.addSublayer(imageLayer)
}
private func compositionLayerInstruction(for track: AVCompositionTrack,assetTrack: AVAssetTrack) -> AVMutableVideoCompositionLayerInstruction {
let instruction = AVMutableVideoCompositionLayerInstruction(assetTrack: track)
let transform = assetTrack.preferredTransform
instruction.setTransform(transform,at: .zero)
return instruction
}
它工作得很好,但是我不知道当URL来自front camera
时是什么原因,所以视频仅显示在视图的上部。
就像一半的视频和一半的黑屏。
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)