Самое популярное короткое видео приложение в данный момент - Дуюн. С его богатыми видео особыми эффектами Дуйин привлек пользу многих молодых пользователей. Сегодня давайте посмотрим на то, как в Интернете реализуются специальные эффекты Дуйина.
основной принцип
Принцип реализации относительно прост, и его можно свести к следующим трем шагам:
- 1. Используйте предварительно обработанный холст для рисования каждого кадра видео.
- 2. Перенести предварительно отрендеренный холст в видеопамять как текстуру.
- 3. Программа-шейдер выполняет постобработку текстуры.
Шаги кажутся простыми, но второй и третий шаги требуют некоторых знаний о WebGL и шейдерах, поэтому не беспокойтесь о том, чего вы не понимаете, вы можете добавить некоторые соответствующие знания.
Основная реализация
Каждый специальный эффект нуждается в поддержке программы JS и программы шейдера, я объясню на примере программы JS и программы шейдера соответственно.
Следующие спецэффекты призваны продемонстрировать мощь и очарование шейдерных программ, поэтому спецэффекты в основном реализованы на стороне шейдеров, так что же делает программа JS?
JS в основном реализует чтение каждого кадра видео, рендеринг его во временный холст и передачу временного холста в качестве текстуры в видеопамять.JS-часть следующих спецэффектов в основном одинакова, поэтому давайте посмотрим на логику JS. первый.
1. Сначала посмотрите на структуру html
<canvas id="canvas"></canvas>
<canvas id="canvasBg" width="256" height="256"></canvas>
<video id="video" src="../img/movie.mp4" controls></video>
Мы разместили два Canvas, первый Canvas используется для отображения спецэффектов, а второй Canvas используется для отрисовки видеокадров, что относительно просто.
2. Затем посмотрите на основной код логики JS.
- Прочитайте видеокадр, визуализируйте его во временном Canvas и передайте временный Canvas в видеопамять в виде текстуры.
ctxBg.drawImage(video, 0, 0, 256, 256);
gl.activeTexture(gl.TEXTURE0);
gl.bindTexture(gl.TEXTURE_2D, texture);
gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, canvasBg);
gl.texParameterf(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR);
gl.texParameterf(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR);
gl.uniform1i(u_Texture, 0);
- Запустите таймер и каждый раз передавайте переменную времени в видеопамять.
function loop() {
if (video.ended) {
return;
}
computeFrame();
time = time + interval;
gl.uniform1f(u_Time, time);
// 清除画布
gl.clear(gl.COLOR_BUFFER_BIT);
if (positions.length <= 0) {
return;
}
//绘制图元设置为三角形。
var primitiveType = gl.TRIANGLES;
//因为我们要绘制6个点,所以执行6次顶点绘制操作。
gl.drawArrays(gl.TRIANGLES, 0, positions.length / 3);
timer = requestAnimationFrame(loop);
}
3. Та часть, которая собственно реализует спецэффекты находится на шейдерной программе.Конечно, исходный код шейдера тоже перенесен из JS в видеопамять.Мы не будем приводить эту часть кода, а только покажем вам различные спецэффекты.
Изображение немного пустое, вы можете не видеть его четко, но вы можете перейти на веб-страницу с образцом, чтобы почувствовать это~
- зум
- мигающий белый
- остаточный образ
- ДУША
- Сбой
Эпилог
Кодовая реализация приведенного выше примера включает в себя некоторые основные операции WebGL, которые довольно объемны.Студенты, которые хотят увидеть пример, могут перейти к моемуgithubчтобы проверить это.
Дружеское напоминание: лучше всего просматривать его на ПК. При просмотре на мобильном терминале все еще возникают некоторые проблемы ~
В конце немного кликните ручонкой и обратите внимание на официальный аккаунт [внешний стек E]~