primocode 8.18.1 → 8.20.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/primocode.js +5 -2
- package/lib/act.js +25 -3
- package/package.json +1 -1
- package/studio/ferramentas/corte.md +46 -5
- package/studio/server.py +89 -2
- package/studio/voz.py +92 -11
- package/studio/web/js/audio.js +35 -2
- package/studio/web/js/player.js +98 -11
- package/studio/web/js/sfx.js +107 -0
- package/studio/web/tool.html +1 -0
- package/studio/web/view.html +1 -0
- package/studio/__pycache__/voz.cpython-311.pyc +0 -0
- package/studio/arquivos/corte-estatico-corte-a5bab.json +0 -150
- package/studio/arquivos/corte-founders-ai-teste-do-player-2de1d.json +0 -65
- package/studio/arquivos/corte-legado-teste.json +0 -1
- package/studio/arquivos/corte-legado2.json +0 -1
- package/studio/arquivos/corte-minimo-2a829.json +0 -24
- package/studio/arquivos/corte-ok-00a3b.json +0 -18
- package/studio/arquivos/corte-ok-1270e.json +0 -22
- package/studio/arquivos/corte-sweep-corte-cfb29.json +0 -147
- package/studio/arquivos/corte-visual-completo-78f50.json +0 -35
- package/studio/arquivos/grade-sweep-grade-0c2f1.json +0 -119
- package/studio/arquivos/prisma-estatico-prisma-d8740.json +0 -182
- package/studio/arquivos/prisma-sweep-prisma-4c58c.json +0 -166
- package/studio/arquivos/prisma-y-b0785.json +0 -52
- package/studio/arquivos/prosa-sweep-prosa-f29cf.json +0 -80
- package/studio/arquivos/tela-estatico-tela-c7daf.json +0 -90
- package/studio/arquivos/tela-sweep-tela-0d2bf.json +0 -84
- package/studio/arquivos/traco-estatico-traco-25872.json +0 -113
- package/studio/arquivos/traco-sweep-traco-0bcf4.json +0 -102
package/studio/web/js/player.js
CHANGED
|
@@ -33,8 +33,17 @@
|
|
|
33
33
|
function duracaoDe(i) {
|
|
34
34
|
/* "duracao": "3s" (texto) fazia acc virar concatenação e o relógio dava
|
|
35
35
|
vídeo de 00:00. Número são ou o padrão — nunca corrente de texto. */
|
|
36
|
-
var
|
|
37
|
-
|
|
36
|
+
var c = cenas[i] || {};
|
|
37
|
+
var d = Number(c.duracao);
|
|
38
|
+
d = (isFinite(d) && d > 0) ? Math.min(60, d) : 4;
|
|
39
|
+
/* A narração pré-renderizada tem duração conhecida (o servidor mediu o
|
|
40
|
+
WAV e gravou `narracaoDur` na cena). A cena dura o que for MAIOR:
|
|
41
|
+
o que o autor pediu ou a fala inteira + um respiro. É isto que torna
|
|
42
|
+
a linha do tempo determinística — o "cena espera a voz" do laço vira
|
|
43
|
+
só a rede de segurança para narração sintetizada na hora. */
|
|
44
|
+
var n = Number(c.narracaoDur);
|
|
45
|
+
if (isFinite(n) && n > 0 && c.narracaoAudio) d = Math.max(d, Math.min(90, n + 0.4));
|
|
46
|
+
return d;
|
|
38
47
|
}
|
|
39
48
|
function total() { return cenas.reduce(function (s, _, i) { return s + duracaoDe(i); }, 0); }
|
|
40
49
|
function inicioDe(i) { var s = 0; for (var k = 0; k < i; k++) s += duracaoDe(k); return s; }
|
|
@@ -129,6 +138,7 @@
|
|
|
129
138
|
|
|
130
139
|
function ir(n, semRelogio) {
|
|
131
140
|
if (!cenas.length) return;
|
|
141
|
+
var anterior = atual;
|
|
132
142
|
atual = Math.max(0, Math.min(cenas.length - 1, n));
|
|
133
143
|
Array.prototype.forEach.call(palco.children, function (no, i) {
|
|
134
144
|
no.style.display = i === atual ? "block" : "none";
|
|
@@ -139,6 +149,17 @@
|
|
|
139
149
|
contar(no);
|
|
140
150
|
}
|
|
141
151
|
});
|
|
152
|
+
/* SFX na entrada da cena — só durante a reprodução (navegar com as setas
|
|
153
|
+
não faz barulho) e nunca na primeira montagem. `doc.sfx === false`
|
|
154
|
+
desliga tudo; `cena.sfx` escolhe o efeito ("whoosh" | "impacto" |
|
|
155
|
+
"click" | "nenhum") e ganha do automático por transição. */
|
|
156
|
+
if (sfx && tocando && ehVideo && atual !== anterior && doc.sfx !== false) {
|
|
157
|
+
var cenaNova = cenas[atual] || {};
|
|
158
|
+
if (cenaNova.sfx !== "nenhum") {
|
|
159
|
+
if (cenaNova.sfx && sfx[cenaNova.sfx]) sfx[cenaNova.sfx]();
|
|
160
|
+
else sfx.transicao(cenaNova.transicao, atual);
|
|
161
|
+
}
|
|
162
|
+
}
|
|
142
163
|
narrar();
|
|
143
164
|
pintarApresentador();
|
|
144
165
|
if (!semRelogio) decorrido = inicioDe(atual);
|
|
@@ -255,6 +276,7 @@
|
|
|
255
276
|
function narrar() {
|
|
256
277
|
if (typeof Narracao !== "undefined") Narracao.parar();
|
|
257
278
|
if (vozGravada) { vozGravada.pause(); vozGravada = null; }
|
|
279
|
+
if (trilha && trilha.duck) trilha.duck(false);
|
|
258
280
|
if (mudo || doc.narracao === false) return;
|
|
259
281
|
|
|
260
282
|
var cena = cenas[atual] || {};
|
|
@@ -263,13 +285,35 @@
|
|
|
263
285
|
if (cena.narracaoAudio) {
|
|
264
286
|
vozGravada = new Audio(cena.narracaoAudio);
|
|
265
287
|
vozGravada.volume = (doc.voz && doc.voz.volume != null) ? doc.voz.volume : 1;
|
|
288
|
+
/* Pelo grafo da trilha, quando ele existe: a voz entra na gravação MP4
|
|
289
|
+
sem "compartilhar áudio da aba", e a música cede espaço (duck)
|
|
290
|
+
enquanto a fala dura. Sem grafo, toca direto como antes. */
|
|
291
|
+
if (trilha && trilha.ctx && trilha.entradaVoz) {
|
|
292
|
+
try {
|
|
293
|
+
var fonteVoz = trilha.ctx.createMediaElementSource(vozGravada);
|
|
294
|
+
fonteVoz.connect(trilha.entradaVoz);
|
|
295
|
+
} catch (_) { /* elemento já conectado ou grafo indisponível */ }
|
|
296
|
+
if (trilha.duck) {
|
|
297
|
+
trilha.duck(true);
|
|
298
|
+
vozGravada.onended = function () { if (trilha && trilha.duck) trilha.duck(false); };
|
|
299
|
+
}
|
|
300
|
+
}
|
|
266
301
|
var p = vozGravada.play();
|
|
267
302
|
if (p && p.catch) p.catch(function () {});
|
|
268
303
|
return;
|
|
269
304
|
}
|
|
270
305
|
|
|
271
306
|
if (typeof Narracao === "undefined" || !Narracao.disponivel()) return;
|
|
272
|
-
if (cena.narracao)
|
|
307
|
+
if (cena.narracao) {
|
|
308
|
+
if (trilha && trilha.duck) {
|
|
309
|
+
trilha.duck(true);
|
|
310
|
+
Narracao.falar(cena.narracao, doc.voz || {}).then(function () {
|
|
311
|
+
if (trilha && trilha.duck) trilha.duck(false);
|
|
312
|
+
});
|
|
313
|
+
} else {
|
|
314
|
+
Narracao.falar(cena.narracao, doc.voz || {});
|
|
315
|
+
}
|
|
316
|
+
}
|
|
273
317
|
}
|
|
274
318
|
|
|
275
319
|
/* ----------------------------------------------------- apresentador --- */
|
|
@@ -317,11 +361,18 @@
|
|
|
317
361
|
|
|
318
362
|
/* ------------------------------------------------------------ trilha -- */
|
|
319
363
|
|
|
364
|
+
var sfx = null;
|
|
365
|
+
|
|
320
366
|
function prepararTrilha() {
|
|
321
|
-
var cfg = doc.trilha;
|
|
322
|
-
if (!cfg || (!cfg.src && cfg.tipo !== "gerada")) return;
|
|
323
367
|
if (typeof criarTrilha !== "function") return;
|
|
368
|
+
var cfg = doc.trilha;
|
|
369
|
+
/* Sem trilha o grafo ainda nasce (tipo "nenhuma"): é por ele que a
|
|
370
|
+
narração e os SFX entram na gravação MP4. */
|
|
371
|
+
if (!cfg || (!cfg.src && cfg.tipo !== "gerada")) cfg = { tipo: "nenhuma" };
|
|
324
372
|
trilha = criarTrilha(cfg, function (msg) { aviso(msg, 3000); });
|
|
373
|
+
if (trilha && trilha.ctx && trilha.no && typeof criarSfx === "function" && doc.sfx !== false) {
|
|
374
|
+
sfx = criarSfx(trilha.ctx, trilha.no);
|
|
375
|
+
}
|
|
325
376
|
}
|
|
326
377
|
|
|
327
378
|
/* --------------------------------------------------------- transporte -- */
|
|
@@ -337,7 +388,7 @@
|
|
|
337
388
|
'<div class="tp-tempo" id="tp-total">00:00</div>' +
|
|
338
389
|
'<button class="tp-btn pequeno" id="tp-som" title="Mudo (M)"></button>' +
|
|
339
390
|
'<input class="tp-vol" id="tp-vol" type="range" min="0" max="100" value="70">' +
|
|
340
|
-
'<button class="tp-btn texto" id="tp-gravar" title="
|
|
391
|
+
'<button class="tp-btn texto primo" id="tp-gravar" title="Baixar este vídeo como arquivo">Baixar MP4</button>';
|
|
341
392
|
document.body.appendChild(transporte);
|
|
342
393
|
|
|
343
394
|
document.getElementById("tp-tocar").onclick = function () { tocando ? pausar() : tocar(); };
|
|
@@ -393,14 +444,47 @@
|
|
|
393
444
|
iniciarGravacao();
|
|
394
445
|
}
|
|
395
446
|
|
|
447
|
+
/* O melhor formato que este navegador sabe gravar.
|
|
448
|
+
*
|
|
449
|
+
* A ordem importa: H.264 com AAC é o MP4 que toca em qualquer lugar —
|
|
450
|
+
* WhatsApp, Instagram, PowerPoint, TV. AV1 em MP4 é MP4 de verdade mas ainda
|
|
451
|
+
* não toca em tudo, então vem depois. O webm é o último recurso: abre em
|
|
452
|
+
* navegador e pouco mais.
|
|
453
|
+
*/
|
|
454
|
+
var FORMATOS = [
|
|
455
|
+
"video/mp4;codecs=avc1.42E01E,mp4a.40.2",
|
|
456
|
+
"video/mp4;codecs=avc1,mp4a.40.2",
|
|
457
|
+
"video/mp4;codecs=avc1",
|
|
458
|
+
"video/mp4",
|
|
459
|
+
"video/webm;codecs=vp9,opus",
|
|
460
|
+
"video/webm",
|
|
461
|
+
];
|
|
462
|
+
|
|
463
|
+
function escolherFormato() {
|
|
464
|
+
for (var i = 0; i < FORMATOS.length; i++) {
|
|
465
|
+
if (MediaRecorder.isTypeSupported(FORMATOS[i])) return FORMATOS[i];
|
|
466
|
+
}
|
|
467
|
+
return "video/webm";
|
|
468
|
+
}
|
|
469
|
+
|
|
470
|
+
function gravaMp4() { return /mp4/.test(escolherFormato()); }
|
|
471
|
+
|
|
396
472
|
function iniciarGravacao() {
|
|
397
473
|
if (!navigator.mediaDevices || !navigator.mediaDevices.getDisplayMedia) {
|
|
398
474
|
return aviso("este navegador não grava a tela", 3000);
|
|
399
475
|
}
|
|
400
476
|
// audio:true deixa o usuário marcar "compartilhar áudio da aba" — é assim
|
|
401
477
|
// que a narração falada entra na gravação
|
|
478
|
+
// preferCurrentTab tira o passo de escolher a janela: o Chrome já vem
|
|
479
|
+
// com ESTA aba selecionada, então baixar vira um clique e um "permitir"
|
|
480
|
+
// em vez de um clique, uma escolha e um "permitir".
|
|
402
481
|
navigator.mediaDevices.getDisplayMedia({
|
|
403
482
|
video: { frameRate: 30 }, audio: true,
|
|
483
|
+
preferCurrentTab: true, selfBrowserSurface: "include",
|
|
484
|
+
}).catch(function () {
|
|
485
|
+
// Navegador que não conhece preferCurrentTab recusa o pedido inteiro:
|
|
486
|
+
// repete sem as opções novas em vez de falhar.
|
|
487
|
+
return navigator.mediaDevices.getDisplayMedia({ video: { frameRate: 30 }, audio: true });
|
|
404
488
|
}).then(function (fluxo) {
|
|
405
489
|
fluxoTela = fluxo;
|
|
406
490
|
var faixas = fluxo.getVideoTracks();
|
|
@@ -410,11 +494,14 @@
|
|
|
410
494
|
}
|
|
411
495
|
var misto = new MediaStream(faixas);
|
|
412
496
|
pedacos = [];
|
|
413
|
-
// MP4 primeiro,
|
|
414
|
-
//
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
497
|
+
// MP4 primeiro, e testando os codecs NOMEADOS antes do genérico.
|
|
498
|
+
//
|
|
499
|
+
// Testar só "video/mp4" perdia MP4 em navegador que existe: o Chrome
|
|
500
|
+
// responde false para o nome solto e true para
|
|
501
|
+
// "video/mp4;codecs=avc1.42E01E,mp4a.40.2". Quem pediu MP4 recebia
|
|
502
|
+
// webm à toa. A lista vai do mais compatível (H.264 + AAC, que toca em
|
|
503
|
+
// tudo) para o menos, e só cai no webm quando não há MP4 nenhum.
|
|
504
|
+
var tipo = escolherFormato();
|
|
418
505
|
gravador = new MediaRecorder(misto, { mimeType: tipo, videoBitsPerSecond: 8000000 });
|
|
419
506
|
gravador.ondataavailable = function (ev) { if (ev.data.size) pedacos.push(ev.data); };
|
|
420
507
|
gravador.onstop = baixarGravacao;
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
/* ==========================================================================
|
|
2
|
+
sfx.js — efeitos sonoros do Corte, sintetizados na hora.
|
|
3
|
+
|
|
4
|
+
Nenhum arquivo, nenhuma licença: whoosh é ruído filtrado com varredura,
|
|
5
|
+
impacto é um seno grave despencando, click é um blip curto. Tudo entra no
|
|
6
|
+
mesmo grafo da trilha (via `destino`), então a gravação MP4 captura os
|
|
7
|
+
efeitos junto — sem depender de "compartilhar áudio da aba".
|
|
8
|
+
|
|
9
|
+
Uso:
|
|
10
|
+
var sfx = criarSfx(ctx, destino); // destino: nó do grafo (compressor)
|
|
11
|
+
sfx.whoosh(); // transição de cena
|
|
12
|
+
sfx.impacto(); // ênfase (flash, número grande)
|
|
13
|
+
sfx.click(); // entrada de elemento, feedback discreto
|
|
14
|
+
|
|
15
|
+
O volume de cada efeito já vem calibrado para sentar SOB a narração.
|
|
16
|
+
========================================================================== */
|
|
17
|
+
|
|
18
|
+
function criarSfx(ctx, destino) {
|
|
19
|
+
"use strict";
|
|
20
|
+
if (!ctx || !destino) return null;
|
|
21
|
+
|
|
22
|
+
var saida = ctx.createGain();
|
|
23
|
+
saida.gain.value = 1;
|
|
24
|
+
saida.connect(destino);
|
|
25
|
+
|
|
26
|
+
var ruido = null;
|
|
27
|
+
function bufferRuido() {
|
|
28
|
+
if (ruido) return ruido;
|
|
29
|
+
ruido = ctx.createBuffer(1, ctx.sampleRate * 1.2, ctx.sampleRate);
|
|
30
|
+
var d = ruido.getChannelData(0);
|
|
31
|
+
for (var i = 0; i < d.length; i++) d[i] = Math.random() * 2 - 1;
|
|
32
|
+
return ruido;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
/* Varredura de ruído — o "passar de página" do vídeo. `variacao` muda o
|
|
36
|
+
miolo da varredura para os whooshes não saírem todos idênticos. */
|
|
37
|
+
function whoosh(variacao) {
|
|
38
|
+
var agora = ctx.currentTime;
|
|
39
|
+
var v = (variacao == null ? Math.random() : variacao) % 1;
|
|
40
|
+
var s = ctx.createBufferSource(), g = ctx.createGain(), f = ctx.createBiquadFilter();
|
|
41
|
+
s.buffer = bufferRuido();
|
|
42
|
+
f.type = "bandpass";
|
|
43
|
+
f.Q.value = 1.1;
|
|
44
|
+
f.frequency.setValueAtTime(300 + v * 300, agora);
|
|
45
|
+
f.frequency.exponentialRampToValueAtTime(2200 + v * 1400, agora + 0.16);
|
|
46
|
+
f.frequency.exponentialRampToValueAtTime(500, agora + 0.42);
|
|
47
|
+
g.gain.setValueAtTime(0.0001, agora);
|
|
48
|
+
g.gain.exponentialRampToValueAtTime(0.11, agora + 0.10);
|
|
49
|
+
g.gain.exponentialRampToValueAtTime(0.0001, agora + 0.45);
|
|
50
|
+
s.connect(f); f.connect(g); g.connect(saida);
|
|
51
|
+
s.start(agora); s.stop(agora + 0.5);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
/* Seno grave despencando + um sopro de ruído no ataque. */
|
|
55
|
+
function impacto() {
|
|
56
|
+
var agora = ctx.currentTime;
|
|
57
|
+
var o = ctx.createOscillator(), g = ctx.createGain();
|
|
58
|
+
o.type = "sine";
|
|
59
|
+
o.frequency.setValueAtTime(120, agora);
|
|
60
|
+
o.frequency.exponentialRampToValueAtTime(36, agora + 0.5);
|
|
61
|
+
g.gain.setValueAtTime(0.30, agora);
|
|
62
|
+
g.gain.exponentialRampToValueAtTime(0.0001, agora + 0.9);
|
|
63
|
+
o.connect(g); g.connect(saida);
|
|
64
|
+
o.start(agora); o.stop(agora + 1.0);
|
|
65
|
+
|
|
66
|
+
var s = ctx.createBufferSource(), gr = ctx.createGain(), f = ctx.createBiquadFilter();
|
|
67
|
+
s.buffer = bufferRuido();
|
|
68
|
+
f.type = "lowpass";
|
|
69
|
+
f.frequency.value = 900;
|
|
70
|
+
gr.gain.setValueAtTime(0.09, agora);
|
|
71
|
+
gr.gain.exponentialRampToValueAtTime(0.0001, agora + 0.22);
|
|
72
|
+
s.connect(f); f.connect(gr); gr.connect(saida);
|
|
73
|
+
s.start(agora); s.stop(agora + 0.3);
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/* Blip de interface: curto, agudo, discreto. */
|
|
77
|
+
function click() {
|
|
78
|
+
var agora = ctx.currentTime;
|
|
79
|
+
var o = ctx.createOscillator(), g = ctx.createGain();
|
|
80
|
+
o.type = "sine";
|
|
81
|
+
o.frequency.setValueAtTime(2100, agora);
|
|
82
|
+
g.gain.setValueAtTime(0.06, agora);
|
|
83
|
+
g.gain.exponentialRampToValueAtTime(0.0001, agora + 0.05);
|
|
84
|
+
o.connect(g); g.connect(saida);
|
|
85
|
+
o.start(agora); o.stop(agora + 0.07);
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
/* O efeito certo para a ENTRADA de uma cena, pela transição dela.
|
|
89
|
+
flash e zoom pedem peso; corte seco não pede nada. */
|
|
90
|
+
function transicao(tipo, indice) {
|
|
91
|
+
if (tipo === "corte") return;
|
|
92
|
+
if (tipo === "flash" || tipo === "zoom") return impacto();
|
|
93
|
+
whoosh(((indice || 0) * 0.37) % 1);
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
return {
|
|
97
|
+
whoosh: whoosh,
|
|
98
|
+
impacto: impacto,
|
|
99
|
+
click: click,
|
|
100
|
+
transicao: transicao,
|
|
101
|
+
volume: function (v) { saida.gain.value = v; },
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
if (typeof module !== "undefined" && module.exports) {
|
|
106
|
+
module.exports = { criarSfx: criarSfx };
|
|
107
|
+
}
|
package/studio/web/tool.html
CHANGED
|
@@ -67,6 +67,7 @@
|
|
|
67
67
|
document.getElementById("btn-baixar").innerHTML = svgIcone("baixar");
|
|
68
68
|
</script>
|
|
69
69
|
<script src="/js/audio.js"></script>
|
|
70
|
+
<script src="/js/sfx.js"></script>
|
|
70
71
|
<script src="/js/voz-neural.js"></script>
|
|
71
72
|
<script src="/js/narracao.js"></script>
|
|
72
73
|
<script src="/js/midia.js"></script>
|
package/studio/web/view.html
CHANGED
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
<script src="/js/render-prosa.js"></script>
|
|
18
18
|
<script src="/js/render-grade.js"></script>
|
|
19
19
|
<script src="/js/audio.js"></script>
|
|
20
|
+
<script src="/js/sfx.js"></script>
|
|
20
21
|
<script src="/js/voz-neural.js"></script>
|
|
21
22
|
<script src="/js/narracao.js"></script>
|
|
22
23
|
<script src="/js/player.js"></script>
|
|
Binary file
|
|
@@ -1,150 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"id": "corte-estatico-corte-a5bab",
|
|
3
|
-
"ferramenta": "corte",
|
|
4
|
-
"titulo": "estatico-corte",
|
|
5
|
-
"doc": {
|
|
6
|
-
"tema": "brasa",
|
|
7
|
-
"largura": 1080,
|
|
8
|
-
"altura": 1920,
|
|
9
|
-
"acabamento": "grao",
|
|
10
|
-
"trilha": {
|
|
11
|
-
"tipo": "gerada",
|
|
12
|
-
"estilo": "pulso",
|
|
13
|
-
"volume": 0.7
|
|
14
|
-
},
|
|
15
|
-
"cenas": [
|
|
16
|
-
{
|
|
17
|
-
"layout": "centro",
|
|
18
|
-
"duracao": 3,
|
|
19
|
-
"fundo": "aurora",
|
|
20
|
-
"transicao": "flash",
|
|
21
|
-
"elementos": [
|
|
22
|
-
{
|
|
23
|
-
"tipo": "texto",
|
|
24
|
-
"papel": "titulo",
|
|
25
|
-
"texto": "Sua conta subiu\nde novo.",
|
|
26
|
-
"tamanho": 124,
|
|
27
|
-
"estilo": "gradiente",
|
|
28
|
-
"anim": "nenhuma"
|
|
29
|
-
}
|
|
30
|
-
]
|
|
31
|
-
},
|
|
32
|
-
{
|
|
33
|
-
"layout": "centro",
|
|
34
|
-
"duracao": 3,
|
|
35
|
-
"fundo": "vinheta",
|
|
36
|
-
"transicao": "limpar",
|
|
37
|
-
"elementos": [
|
|
38
|
-
{
|
|
39
|
-
"tipo": "texto",
|
|
40
|
-
"papel": "titulo",
|
|
41
|
-
"texto": "E não foi o seu chuveiro.",
|
|
42
|
-
"tamanho": 78,
|
|
43
|
-
"estilo": "marcador",
|
|
44
|
-
"anim": "nenhuma"
|
|
45
|
-
}
|
|
46
|
-
]
|
|
47
|
-
},
|
|
48
|
-
{
|
|
49
|
-
"layout": "centro",
|
|
50
|
-
"duracao": 4,
|
|
51
|
-
"transicao": "zoom",
|
|
52
|
-
"acabamento": "vinheta",
|
|
53
|
-
"fundo": {
|
|
54
|
-
"imagem": "/midia/torre.jpg",
|
|
55
|
-
"escurecer": 0.5
|
|
56
|
-
},
|
|
57
|
-
"elementos": [
|
|
58
|
-
{
|
|
59
|
-
"tipo": "numeros",
|
|
60
|
-
"contar": true,
|
|
61
|
-
"anim": "nenhuma",
|
|
62
|
-
"tamanho": 180,
|
|
63
|
-
"itens": [
|
|
64
|
-
"+38% | bandeira tarifária em 12 meses"
|
|
65
|
-
]
|
|
66
|
-
}
|
|
67
|
-
]
|
|
68
|
-
},
|
|
69
|
-
{
|
|
70
|
-
"layout": "livre",
|
|
71
|
-
"duracao": 4,
|
|
72
|
-
"transicao": "deslizar",
|
|
73
|
-
"elementos": [
|
|
74
|
-
{
|
|
75
|
-
"tipo": "imagem",
|
|
76
|
-
"src": "/midia/campo.jpg",
|
|
77
|
-
"x": 0,
|
|
78
|
-
"y": 0,
|
|
79
|
-
"l": 1080,
|
|
80
|
-
"a": 1920,
|
|
81
|
-
"raio": 0,
|
|
82
|
-
"movimento": "aproximar",
|
|
83
|
-
"filtro": "contraste",
|
|
84
|
-
"anim": "nenhuma"
|
|
85
|
-
},
|
|
86
|
-
{
|
|
87
|
-
"tipo": "forma",
|
|
88
|
-
"forma": "retangulo",
|
|
89
|
-
"x": 0,
|
|
90
|
-
"y": 1180,
|
|
91
|
-
"l": 1080,
|
|
92
|
-
"a": 740,
|
|
93
|
-
"preenchimento": "rgba(10,5,6,.72)",
|
|
94
|
-
"anim": "nenhuma"
|
|
95
|
-
},
|
|
96
|
-
{
|
|
97
|
-
"tipo": "texto",
|
|
98
|
-
"x": 90,
|
|
99
|
-
"y": 1320,
|
|
100
|
-
"l": 900,
|
|
101
|
-
"a": 420,
|
|
102
|
-
"texto": "O custo está\nna transmissão",
|
|
103
|
-
"tamanho": 104,
|
|
104
|
-
"peso": 750,
|
|
105
|
-
"estilo": "sombra",
|
|
106
|
-
"anim": "nenhuma"
|
|
107
|
-
}
|
|
108
|
-
]
|
|
109
|
-
},
|
|
110
|
-
{
|
|
111
|
-
"layout": "centro",
|
|
112
|
-
"duracao": 5,
|
|
113
|
-
"fundo": "raios",
|
|
114
|
-
"transicao": "subir",
|
|
115
|
-
"elementos": [
|
|
116
|
-
{
|
|
117
|
-
"tipo": "lista",
|
|
118
|
-
"revelar": true,
|
|
119
|
-
"tamanho": 52,
|
|
120
|
-
"intervalo": 0.9,
|
|
121
|
-
"itens": [
|
|
122
|
-
"Linhas saturadas no Nordeste",
|
|
123
|
-
"Usina gerando sem escoar",
|
|
124
|
-
"A conta chega em quem consome"
|
|
125
|
-
],
|
|
126
|
-
"anim": "nenhuma"
|
|
127
|
-
}
|
|
128
|
-
]
|
|
129
|
-
},
|
|
130
|
-
{
|
|
131
|
-
"layout": "centro",
|
|
132
|
-
"duracao": 3,
|
|
133
|
-
"fundo": "brilho",
|
|
134
|
-
"transicao": "fade",
|
|
135
|
-
"acabamento": "luz",
|
|
136
|
-
"elementos": [
|
|
137
|
-
{
|
|
138
|
-
"tipo": "texto",
|
|
139
|
-
"papel": "titulo",
|
|
140
|
-
"texto": "Segue para\nentender a próxima.",
|
|
141
|
-
"tamanho": 96,
|
|
142
|
-
"estilo": "contorno-tom",
|
|
143
|
-
"anim": "nenhuma"
|
|
144
|
-
}
|
|
145
|
-
]
|
|
146
|
-
}
|
|
147
|
-
]
|
|
148
|
-
},
|
|
149
|
-
"atualizado": "2026-08-16T15:08:28+00:00"
|
|
150
|
-
}
|
|
@@ -1,65 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"id": "corte-founders-ai-teste-do-player-2de1d",
|
|
3
|
-
"ferramenta": "corte",
|
|
4
|
-
"titulo": "Founders AI — teste do player",
|
|
5
|
-
"doc": {
|
|
6
|
-
"tema": "brasa",
|
|
7
|
-
"largura": 1080,
|
|
8
|
-
"altura": 1920,
|
|
9
|
-
"acabamento": "grao",
|
|
10
|
-
"trilha": {
|
|
11
|
-
"tipo": "gerada",
|
|
12
|
-
"estilo": "pulso",
|
|
13
|
-
"volume": 0.7
|
|
14
|
-
},
|
|
15
|
-
"cenas": [
|
|
16
|
-
{
|
|
17
|
-
"layout": "centro",
|
|
18
|
-
"duracao": 3,
|
|
19
|
-
"fundo": "aurora",
|
|
20
|
-
"transicao": "flash",
|
|
21
|
-
"elementos": [
|
|
22
|
-
{
|
|
23
|
-
"tipo": "texto",
|
|
24
|
-
"papel": "titulo",
|
|
25
|
-
"texto": "Imersão\nFounders AI",
|
|
26
|
-
"tamanho": 124,
|
|
27
|
-
"estilo": "gradiente",
|
|
28
|
-
"anim": "desfoque"
|
|
29
|
-
}
|
|
30
|
-
]
|
|
31
|
-
},
|
|
32
|
-
{
|
|
33
|
-
"layout": "centro",
|
|
34
|
-
"duracao": 3,
|
|
35
|
-
"fundo": "vinheta",
|
|
36
|
-
"elementos": [
|
|
37
|
-
{
|
|
38
|
-
"tipo": "texto",
|
|
39
|
-
"papel": "titulo",
|
|
40
|
-
"texto": "Paris Group · Chapecó",
|
|
41
|
-
"tamanho": 78,
|
|
42
|
-
"estilo": "marcador",
|
|
43
|
-
"anim": "palavra"
|
|
44
|
-
}
|
|
45
|
-
]
|
|
46
|
-
},
|
|
47
|
-
{
|
|
48
|
-
"layout": "centro",
|
|
49
|
-
"duracao": 4,
|
|
50
|
-
"fundo": "raios",
|
|
51
|
-
"elementos": [
|
|
52
|
-
{
|
|
53
|
-
"tipo": "numeros",
|
|
54
|
-
"contar": true,
|
|
55
|
-
"tamanho": 180,
|
|
56
|
-
"itens": [
|
|
57
|
-
"20 | empresários por turma"
|
|
58
|
-
]
|
|
59
|
-
}
|
|
60
|
-
]
|
|
61
|
-
}
|
|
62
|
-
]
|
|
63
|
-
},
|
|
64
|
-
"atualizado": "2026-08-16T14:55:24+00:00"
|
|
65
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"id": "corte-legado-teste", "ferramenta": "corte", "titulo": "legado", "doc": {"tema": "meia-noite", "largura": 1080, "altura": 1920, "cenas": [{"duracao": "4s", "fundo": "aurora", "elementos": [{"tipo": "titulo", "texto": "Imersão Founders AI"}, {"tipo": "subtitulo", "conteudo": "Paris Group · Chapecó"}]}]}}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"id": "corte-legado2", "ferramenta": "corte", "titulo": "legado2", "doc": {"tema": "meia-noite", "largura": 1080, "altura": 1920, "cenas": [{"duracao": "4s", "fundo": "aurora", "elementos": [{"tipo": "titulo", "texto": "Imersão Founders AI", "anim": "nenhuma"}, {"tipo": "subtitulo", "conteudo": "Paris Group · Chapecó", "anim": "nenhuma"}]}]}}
|
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"id": "corte-minimo-2a829",
|
|
3
|
-
"ferramenta": "corte",
|
|
4
|
-
"titulo": "minimo",
|
|
5
|
-
"doc": {
|
|
6
|
-
"tema": "claro",
|
|
7
|
-
"largura": 1080,
|
|
8
|
-
"altura": 1920,
|
|
9
|
-
"cenas": [
|
|
10
|
-
{
|
|
11
|
-
"layout": "centro",
|
|
12
|
-
"duracao": 5,
|
|
13
|
-
"elementos": [
|
|
14
|
-
{
|
|
15
|
-
"tipo": "texto",
|
|
16
|
-
"texto": "TESTE VISIVEL",
|
|
17
|
-
"tamanho": 120
|
|
18
|
-
}
|
|
19
|
-
]
|
|
20
|
-
}
|
|
21
|
-
]
|
|
22
|
-
},
|
|
23
|
-
"atualizado": "2026-08-16T14:57:24+00:00"
|
|
24
|
-
}
|
|
@@ -1,22 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"id": "corte-ok-1270e",
|
|
3
|
-
"ferramenta": "corte",
|
|
4
|
-
"titulo": "ok",
|
|
5
|
-
"doc": {
|
|
6
|
-
"tema": "brasa",
|
|
7
|
-
"cenas": [
|
|
8
|
-
{
|
|
9
|
-
"duracao": 3,
|
|
10
|
-
"elementos": [
|
|
11
|
-
{
|
|
12
|
-
"tipo": "texto",
|
|
13
|
-
"papel": "titulo",
|
|
14
|
-
"texto": "Founders AI",
|
|
15
|
-
"anim": "nenhuma"
|
|
16
|
-
}
|
|
17
|
-
]
|
|
18
|
-
}
|
|
19
|
-
]
|
|
20
|
-
},
|
|
21
|
-
"atualizado": "2026-08-16T17:50:21+00:00"
|
|
22
|
-
}
|