已解决-如何在SceneKit中使用“带有Alpha通道的HEVC”视频?

问题描述 投票:2回答:1

[At WWDC 2019, Apple announced that it was now handling HEVC with Alpha in iOS,并声明可以在SceneKit中使用它。

我已经尝试了好几个小时才能做到这一点,没有任何运气。

我的目标是将视频用作SCNNode平面上的纹理,并在视频透明的地方使该平面透明。

我使用HEVC和Apple在this xcode project中提供的Alpha视频(带有2个木偶的视频)。

[我正在使用iOS 13.2在真实设备上使用XCode 11.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用作我的SCNNode的材质的漫反射+材质内容

这似乎是在SceneKit中将视频显示为素材的一种常见方法。另外,在the example provided by apple中,有关如何使用“ alpha渲染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]。'

注意:使用不带Alpha通道的常规HEVC视频时,不会出现此错误。

方法3.使用材质着色器将Alpha值从视频复制到材质的透明贴图。

let material = SCNMaterial()
material.diffuse.contents = player
material.shaderModifiers = [
    SCNShaderModifierEntryPoint.surface :  "_surface.transparent.a = _surface.diffuse.a;"
];
plane?.geometry?.materials = [material];

结果:视频以黑色像素而不是透明像素呈现。 Alpha信息似乎不在_ surface.diffuse.a

方法4.将着色器与SKScene而不是AVPlayer一起使用

结果:与方法2相同的错误。

有人知道如何进行这项工作吗?

更新:2020年1月7日,星期二

我在iOS 13.3和XCode 11.3中尝试了不同的方法。=>结果相同。

我刚刚将错误报告给了Apple,感谢@mnuages的链接。

更新:2020年3月24日,星期二

此问题已在iOS 13.4发行版中修复。

HEVC具有透明性的视频会在SceneKit中立即得到考虑,而无需弄乱材质的透明内容或着色器。

ios swift scenekit
1个回答
1
投票

第一个代码段应该起作用(无需设置transparent材质属性)。如果您在macOS SceneKit游戏模板中进行以下更改,您将获得正确的结果,但是不适用于iOS SceneKit游戏模板。

// retrieve the ship node
let ship = scene.rootNode.childNode(withName: "ship", recursively: true)!
let videoURL = Bundle.main.url(forResource: "puppets_with_alpha_hevc", withExtension: "mov", subdirectory: "art.scnassets");
let player = AVPlayer(url: videoURL! as URL)
let material = SCNMaterial()
material.diffuse.contents = player
player.play();
ship.enumerateHierarchy { (node, _) in
    if let geometry = node.geometry {
        geometry.materials = [material];
    }
}

这种情况下,可能需要file a bug来修复iOS版本。

© www.soinside.com 2019 - 2024. All rights reserved.