На WWDC 2019 Apple объявила, что теперь она обрабатывает HEVC с Alpha в iOS , и заявляет, что она может быть использована в SceneKit.
Я часами пыталсябез удачи.
Моя цель - использовать видео в качестве текстуры на плоскости SCNNode и сделать эту плоскость прозрачной там, где видео прозрачно.
Я использую HEVC с альфа-видео, предоставленным Apple в этом проекте xcode (видео с 2 марионетками).
Я работаю с XCode 11.2 на реальном устройстве с iOS 13.2.
Я пробовал разные подходы.
Подход 1. Использование AVPlayer в качестве диффузного + прозрачного содержимого моегоМатериал SCNNode
let videoURL = Bundle.main.url(forResource: “puppets_with_alpha_hevc“, withExtension: "mov", subdirectory: "Assets.scnassets");
let player = AVPlayer(url: videoURL! as URL)
let material = SCNMaterial()
material.diffuse.contents = player
material.transparent.contents = player
plane?.geometry?.materials = [material];
player.play();
Результат: видео воспроизводится с черными пикселями вместо прозрачных.
Подход 2. Вставьте AVPlayer в SKVideoNode, затем внедритеSKVideoNode в SKScene и используйте SKScene в качестве содержимого diffuse + для материала моего SCNNode
. Это, похоже, распространенный способ отображения видео в качестве материала в SceneKit. Кроме того, в примере, представленном Apple о том, как визуализировать «видео HEVC с альфа», они используют SKVideoNode (но не в контексте SceneKit).
let videoNode = SKVideoNode(avPlayer: player)
let spritescene = SKScene(size: CGSize(width: 360, height: 480))
let spriteKitScene = SKScene(size: CGSize(width: 360.0 / 2.0, height: 480.0 / 2.0))
spriteKitScene.scaleMode = .aspectFit
videoNode.position = CGPoint(x: spriteKitScene.size.width / 2.0, y: spriteKitScene.size.height / 2.0)
videoNode.size = spriteKitScene.size
spriteKitScene.addChild(videoNode)
let material = SCNMaterial()
material.diffuse.contents = spriteKitScene
material.transparent.contents = spriteKitScene
plane?.geometry?.materials = [material];
Результат: получить этот сбой:
validateFunctionArguments: 3577: сбой утверждения `Функция фрагмента (FastSingle_FragFunc): отсутствует привязка сэмплера по индексу 0 для u_texture_sampler [0]. '
Примечание: Я не получаю эту ошибку, когда использую обычное видео HEVC без альфа-канала.
Подход 3. Используйте шейдер материала, чтобы скопировать альфа-значения извидео на прозрачную карту материала.
let material = SCNMaterial()
material.diffuse.contents = player
material.shaderModifiers = [
SCNShaderModifierEntryPoint.surface : "_surface.transparent.a = _surface.diffuse.a;"
];
plane?.geometry?.materials = [material];
Результат: видео отображается с черными пикселями вместо прозрачных. Альфа-информация, по-видимому, отсутствует в _surface.diffuse.a
Подход 4. Использование шейдера с SKScene вместо AVPlayer
Результат: та же ошибка, что и в подходе 2.
Кто-нибудь знает, как заставить это работать?