mirror of
https://github.com/Swiftgram/Telegram-iOS.git
synced 2025-12-22 22:25:57 +00:00
Various improvements
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
import Foundation
|
||||
import UIKit
|
||||
import AVFoundation
|
||||
import SwiftSignalKit
|
||||
|
||||
@@ -39,3 +40,92 @@ extension AVPlayer {
|
||||
return timer
|
||||
}
|
||||
}
|
||||
|
||||
func textureRotatonForAVAsset(_ asset: AVAsset, mirror: Bool = false) -> TextureRotation {
|
||||
for track in asset.tracks {
|
||||
if track.mediaType == .video {
|
||||
let t = track.preferredTransform
|
||||
if t.a == -1.0 && t.d == -1.0 {
|
||||
return .rotate180Degrees
|
||||
} else if t.a == 1.0 && t.d == 1.0 {
|
||||
return .rotate0Degrees
|
||||
} else if t.b == -1.0 && t.c == 1.0 {
|
||||
return .rotate270Degrees
|
||||
} else if t.a == -1.0 && t.d == 1.0 {
|
||||
return .rotate270Degrees
|
||||
} else if t.a == 1.0 && t.d == -1.0 {
|
||||
return .rotate180Degrees
|
||||
} else {
|
||||
return mirror ? .rotate90DegreesMirrored : .rotate90Degrees
|
||||
}
|
||||
}
|
||||
}
|
||||
return .rotate0Degrees
|
||||
}
|
||||
|
||||
func loadTexture(image: UIImage, device: MTLDevice) -> MTLTexture? {
|
||||
func dataForImage(_ image: UIImage) -> UnsafeMutablePointer<UInt8> {
|
||||
let imageRef = image.cgImage
|
||||
let width = Int(image.size.width)
|
||||
let height = Int(image.size.height)
|
||||
let colorSpace = CGColorSpaceCreateDeviceRGB()
|
||||
|
||||
let rawData = UnsafeMutablePointer<UInt8>.allocate(capacity: width * height * 4)
|
||||
let bytePerPixel = 4
|
||||
let bytesPerRow = bytePerPixel * Int(width)
|
||||
let bitsPerComponent = 8
|
||||
let bitmapInfo = CGBitmapInfo.byteOrder32Little.rawValue + CGImageAlphaInfo.premultipliedFirst.rawValue
|
||||
let context = CGContext.init(data: rawData, width: width, height: height, bitsPerComponent: bitsPerComponent, bytesPerRow: bytesPerRow, space: colorSpace, bitmapInfo: bitmapInfo)
|
||||
context?.draw(imageRef!, in: CGRect(x: 0, y: 0, width: width, height: height))
|
||||
|
||||
return rawData
|
||||
}
|
||||
|
||||
let width = Int(image.size.width * image.scale)
|
||||
let height = Int(image.size.height * image.scale)
|
||||
let bytePerPixel = 4
|
||||
let bytesPerRow = bytePerPixel * width
|
||||
|
||||
var texture : MTLTexture?
|
||||
let region = MTLRegionMake2D(0, 0, Int(width), Int(height))
|
||||
let textureDescriptor = MTLTextureDescriptor.texture2DDescriptor(pixelFormat: .bgra8Unorm, width: width, height: height, mipmapped: false)
|
||||
texture = device.makeTexture(descriptor: textureDescriptor)
|
||||
|
||||
let data = dataForImage(image)
|
||||
texture?.replace(region: region, mipmapLevel: 0, withBytes: data, bytesPerRow: bytesPerRow)
|
||||
|
||||
return texture
|
||||
}
|
||||
|
||||
func pixelBufferToMTLTexture(pixelBuffer: CVPixelBuffer, textureCache: CVMetalTextureCache) -> MTLTexture? {
|
||||
let width = CVPixelBufferGetWidth(pixelBuffer)
|
||||
let height = CVPixelBufferGetHeight(pixelBuffer)
|
||||
|
||||
let format: MTLPixelFormat = .r8Unorm
|
||||
var textureRef : CVMetalTexture?
|
||||
let status = CVMetalTextureCacheCreateTextureFromImage(nil, textureCache, pixelBuffer, nil, format, width, height, 0, &textureRef)
|
||||
if status == kCVReturnSuccess {
|
||||
return CVMetalTextureGetTexture(textureRef!)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func getTextureImage(device: MTLDevice, texture: MTLTexture, mirror: Bool = false) -> UIImage? {
|
||||
let colorSpace = CGColorSpaceCreateDeviceRGB()
|
||||
let context = CIContext(mtlDevice: device, options: [:])
|
||||
guard var ciImage = CIImage(mtlTexture: texture, options: [.colorSpace: colorSpace]) else {
|
||||
return nil
|
||||
}
|
||||
let transform: CGAffineTransform
|
||||
if mirror {
|
||||
transform = CGAffineTransform(-1.0, 0.0, 0.0, -1.0, ciImage.extent.width, ciImage.extent.height)
|
||||
} else {
|
||||
transform = CGAffineTransform(1.0, 0.0, 0.0, -1.0, 0.0, ciImage.extent.height)
|
||||
}
|
||||
ciImage = ciImage.transformed(by: transform)
|
||||
guard let cgImage = context.createCGImage(ciImage, from: CGRect(origin: .zero, size: CGSize(width: ciImage.extent.width, height: ciImage.extent.height))) else {
|
||||
return nil
|
||||
}
|
||||
return UIImage(cgImage: cgImage)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user