Как показать мой AVPlayer в VStack с SwiftUI - PullRequest
1 голос
/ 30 июня 2019

Я создал простой AVPlayer.(Если я не создал это правильно, пожалуйста, помогите мне исправить это ... ?) Я хочу отобразить это в моем VStack с быстрым пользовательским интерфейсом, но я немного застрял ...

Если вхотя бы в библиотеке был компонент AVPlayer View, было бы проще, но я не нашел его в библиотеке ... the

Вот мой код в ContentView.swift:

//
//  ContentView.swift
//  test
//
//  Created by Francis Dolbec on 2019-06-26.
//  Copyright © 2019 Francis Dolbec. All rights reserved.
//

import SwiftUI
import AVKit
import AVFoundation

// MARK: variables
var hauteurMenuBar = NSApplication.shared.mainMenu?.menuBarHeight
var urlVideo = URL(string: "/Users/francisdolbec/Movies/Séries Télé/Rick et Morty/Rick.and.Morty.S01E01.VFQ.HDTV.1080p.x264-Kamek.mp4")
let player = AVPlayer(url: urlVideo!)


struct ContentView : View {
    var body: some View {

        VStack {
            Text("Hello World")
                .frame(maxWidth: .infinity, maxHeight: .infinity)
            Text("PATATE!")
            //player.play()
            }

        .frame(minWidth: 1024, idealWidth: 1440, maxWidth: .infinity, minHeight: (640-hauteurMenuBar!), idealHeight: (900-hauteurMenuBar!), maxHeight: .infinity)

    }
}


#if DEBUG
struct ContentView_Previews : PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}
#endif

Кстати, если есть учебник, показывающий, как сделать видеоплеер с быстрым пользовательским интерфейсом, я был бы очень признателен!

РЕДАКТИРОВАТЬ Я забыл сказать, чтоЯ занимаюсь разработкой приложения macOS .

Ответы [ 2 ]

2 голосов
/ 30 июня 2019

Конечно, вот учебник, Крис Мэш на Medium .

По сути, вы встраиваете AVPlayerLayer в структуру, соответствующую UIViewRepresentable, что вы будете делать для любого UIView компонента, который вы хотите использовать с SwiftUI.

struct PlayerView: UIViewRepresentable {
  func updateUIView(_ uiView: UIView, context: UIViewRepresentableContext<PlayerView>) {
  }

  func makeUIView(context: Context) -> UIView {
    return PlayerUIView(frame: .zero)
  }
}

«Мясо» реализации выполняется в классе PlayerUIView:

class PlayerUIView: UIView {
  private let playerLayer = AVPlayerLayer()

  override init(frame: CGRect) {
    super.init(frame: frame)

    let url = URL(string: “https://bitdash-a.akamaihd.net/content/sintel/hls/playlist.m3u8")!
    let player = AVPlayer(url: url)
    player.play()

    playerLayer.player = player
    layer.addSublayer(playerLayer)
  }

  required init?(coder: NSCoder) {
     fatalError(“init(coder:) has not been implemented”)
  }

  override func layoutSubviews() {
    super.layoutSubviews()
    playerLayer.frame = bounds
  }
}

А потом вы используете это так:

var body: some View {
  PlayerView()
}
1 голос
/ 04 июля 2019

Спасибо Богдану за быстрый ответ и за подобное в учебнике!

Вот код, преобразованный в NSView, чтобы он мог работать для приложений MacOS ...

Вот структура PlayerView:

struct PlayerView: NSViewRepresentable {
    func updateNSView(_ nsView: NSView, context: NSViewRepresentableContext<PlayerView>) {

    }
    func makeNSView(context: Context) -> NSView {
        return PlayerNSView(frame: .zero)
    }
}

Вот класс "мясо", как сказал Богдан:

class PlayerNSView: NSView{
    private let playerLayer = AVPlayerLayer()

    override init(frame:CGRect){
        super.init(frame: frame)
        let urlVideo = URL(string: "https://bitdash-a.akamaihd.net/content/sintel/hls/playlist.m3u8")!
        let player = AVPlayer(url: urlVideo)
        player.play()
        playerLayer.player = player
        if layer == nil{
            layer = CALayer()
        }
        layer?.addSublayer(playerLayer)
    }
    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
    override func layout() {
        super.layout()
        playerLayer.frame = bounds
    }
}

Наконец, вы можете использовать PlayerView(), чтобы добавить AVPlayer в struct ContentView.

...