Upgrade to Pro — share decks privately, control downloads, hide ads and more …

InsertableStreams

Polina Gurtovaya
December 04, 2021
46

 InsertableStreams

Polina Gurtovaya

December 04, 2021
Tweet

Transcript

  1. Смешные шапочки на
    Insertable Streams

    View full-size slide

  2. Начнем с WebRTC…

    View full-size slide

  3. Пересылаем


    видео, аудио, файлики,
    скриншару
    Challenge
    В условиях


    Лагающего интернета


    Злых админов,
    настроивших
    fi
    rewall
    Между


    Большим количеством
    участников


    С разными
    приоритетами
    🧟🧟🧟

    View full-size slide

  4. Как работает WebRTC
    new RTCPeerConnection(…)
    new RTCPeerConnection(…)
    🦄

    View full-size slide

  5. Media: SRTP + SRTCP
    Data: SCTP
    Шифрование


    Работает поверх UDP→быстрее


    Можно терять пакеты, если
    нужно


    Не гарантирует порядок


    Bundling
    DTLS: TLS для UDP

    View full-size slide

  6. Как выглядит пожатое
    видео?

    View full-size slide

  7. Compression: intra & inter

    View full-size slide

  8. Intraframe compression (AV1)

    View full-size slide

  9. Какие кодеки поддерживает ваш браузер?

    View full-size slide

  10. Чего-то не хватает….

    View full-size slide

  11. Insertable-streams
    const stream = await getUserMedia({ video: true });


    const track = stream.getVideoTracks()[0];


    const processor = new MediaStreamTrackProcessor({ track });


    const generator = new MediaStreamTrackGenerator({ kind: 'video' });


    const transformer = new TransformStream({


    async transform(frame, controller) {


    const newFrame = processFrameSomehow(frame);


    videoFrame.close();


    controller.enqueue(newFrame);


    },


    });


    trackProcessor.readable.pipeThrough(transformer).pipeTo(trackGenerator.writable);


    View full-size slide

  12. Как же нарисовать ?

    View full-size slide

  13. Нам нужна нейронка :)

    View full-size slide

  14. Находим точки одевания шапочки
    Выбираем бекенд


    •WebAssembly


    •WebGL


    •WebGPU
    Находим нужную
    модель или грузим свою


    • Лучше использовать
    Lite (Mobile) варианты
    Закидываем в модель
    пиксели


    •getImageData


    •VideoDecoder.decode
    Запускаем модель и
    получаем результат


    View full-size slide

  15. Рисуем
    const silhouette = predictions[0].annotations.silhouette


    const slice = [silhouette[silhouette.length - 4], silhouette[0], silhouette[4]]


    const hatW = slice[2][0] - slice[0][0]


    const hatH = hatW * ratio


    ctx.drawImage(image, slice[0][0] + 0.2 * hatW, slice[0][1] - 0.8 * hatH, hatW, hatH)

    View full-size slide

  16. Крафтим новый поток
    const transformer = new TransformStream({


    async transform(frame, controller) {


    // ...


    const newFrame = new VideoFrame(canvas, { timestamp: frame.timestamp })


    controller.enqueue(newFrame)


    frame.close()


    }})


    trackProcessor.readable.pipeThrough(transformer).pipeTo(trackGenerator.writable)


    const transformedStream = new MediaStream([trackGenerator])


    View full-size slide

  17. Что еще можно делать?
    • Encryption


    • Analytics


    • Transcoding (VideoEncoder)


    • Frame rate change

    View full-size slide

  18. @polina_gurtovaya
    @pgurtovaya
    @evilmartians
    @evilmartians_ru
    evilmartians.com
    Спасибо!
    [email protected]

    View full-size slide