/*
Descrição: Estilos da animação exclusiva da página "Desenvolvimento Web"
           (".webdev-*"), usada no hero no lugar do marcador de imagem
           genérico. Mostra um editor de código (esquerda) com linhas a
           serem "escritas" uma a seguir à outra, e um browser (direita)
           onde a página vai sendo montada em tempo real — cada linha de
           código terminada faz aparecer o elemento correspondente na
           pré-visualização (navbar, título, parágrafos, botão). Quando a
           página fica completa acende o emblema "ONLINE"; depois tudo
           limpa e o ciclo recomeça. Os instantes-chave (uma dupla
           "webdev-type-N"/"webdev-reveal-N" por linha) têm de ficar
           sincronizados entre si.
Autor: Emanuel Borges
Versão: 1.2.0
Última alteração: 2026-10-08
*/

.webdev-frame {
    border-radius: 16px;
    border: 1px solid var(--color-border);
    background-color: var(--color-bg-alt);
    padding: 22px;
}

.webdev-board {
    position: relative;
    width: 100%;
    aspect-ratio: 440 / 300;
    border-radius: 10px;
    overflow: hidden;
    background-color: #0a0f1a;
}

.webdev-scene {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
}

/* ---------- Janelas (editor + browser) ---------- */

.webdev-window {
    fill: #0f1626;
    stroke: #2a3550;
    stroke-width: 2;
}

.webdev-titlebar {
    fill: #141c2e;
}

.webdev-dot {
    opacity: 0.8;
}

.webdev-title-text {
    font-family: var(--font-mono);
    font-size: 9px;
    fill: #9fb3d1;
}

.webdev-url-bar {
    fill: #0b1220;
}

.webdev-url-text {
    font-family: var(--font-mono);
    font-size: 8px;
    fill: #5c6b84;
    text-anchor: middle;
}

.webdev-gutter {
    font-family: var(--font-mono);
    font-size: 7px;
    fill: #2a3550;
}

/* ---------- Linhas de código (escritas uma a seguir à outra) ---------- */

/* Cada linha "escreve-se" da esquerda para a direita — igual à técnica
   usada nas barras do gráfico de "Software de Gestão", só que na
   horizontal: a barra já tem a largura final no HTML, e o "scaleX" (com
   origem à esquerda) é que a revela progressivamente. */
.webdev-code-line {
    transform-box: fill-box;
    transform-origin: 0% 50%;
}

.webdev-code-1 { fill: var(--color-primary-light); animation: webdev-type-1 9s linear infinite; }
.webdev-code-2 { fill: #e8a33d; animation: webdev-type-2 9s linear infinite; }
.webdev-code-3 { fill: #3a4558; animation: webdev-type-3 9s linear infinite; }
.webdev-code-4 { fill: #3a4558; animation: webdev-type-4 9s linear infinite; }
.webdev-code-5 { fill: var(--color-primary-light); animation: webdev-type-5 9s linear infinite; }

@keyframes webdev-type-1 {
    0%, 1%    { transform: scaleX(0); }
    6%        { transform: scaleX(1); }
    60%       { transform: scaleX(1); }
    72%, 100% { transform: scaleX(0); }
}
@keyframes webdev-type-2 {
    0%, 8%    { transform: scaleX(0); }
    14%       { transform: scaleX(1); }
    60%       { transform: scaleX(1); }
    72%, 100% { transform: scaleX(0); }
}
@keyframes webdev-type-3 {
    0%, 16%   { transform: scaleX(0); }
    22%       { transform: scaleX(1); }
    60%       { transform: scaleX(1); }
    72%, 100% { transform: scaleX(0); }
}
@keyframes webdev-type-4 {
    0%, 24%   { transform: scaleX(0); }
    30%       { transform: scaleX(1); }
    60%       { transform: scaleX(1); }
    72%, 100% { transform: scaleX(0); }
}
@keyframes webdev-type-5 {
    0%, 32%   { transform: scaleX(0); }
    38%       { transform: scaleX(1); }
    60%       { transform: scaleX(1); }
    72%, 100% { transform: scaleX(0); }
}

/* ---------- Pré-visualização no browser (aparece elemento a elemento) ---------- */

.webdev-preview-el {
    opacity: 0;
    transform: translateY(6px);
    transform-box: fill-box;
    transform-origin: 50% 50%;
}

.webdev-preview-1 { fill: #1b2436; animation: webdev-reveal-1 9s linear infinite; }
.webdev-preview-2 { fill: var(--color-primary-light); animation: webdev-reveal-2 9s linear infinite; }
.webdev-preview-3 { fill: #3a4558; animation: webdev-reveal-3 9s linear infinite; }
.webdev-preview-4 { fill: #3a4558; animation: webdev-reveal-4 9s linear infinite; }
.webdev-preview-5 { fill: var(--color-primary-light); animation: webdev-reveal-5 9s linear infinite; }

@keyframes webdev-reveal-1 {
    0%, 6%    { opacity: 0; transform: translateY(6px); }
    10%, 60%  { opacity: 1; transform: translateY(0); }
    72%, 100% { opacity: 0; transform: translateY(6px); }
}
@keyframes webdev-reveal-2 {
    0%, 14%   { opacity: 0; transform: translateY(6px); }
    18%, 60%  { opacity: 1; transform: translateY(0); }
    72%, 100% { opacity: 0; transform: translateY(6px); }
}
@keyframes webdev-reveal-3 {
    0%, 22%   { opacity: 0; transform: translateY(6px); }
    26%, 60%  { opacity: 1; transform: translateY(0); }
    72%, 100% { opacity: 0; transform: translateY(6px); }
}
@keyframes webdev-reveal-4 {
    0%, 30%   { opacity: 0; transform: translateY(6px); }
    34%, 60%  { opacity: 1; transform: translateY(0); }
    72%, 100% { opacity: 0; transform: translateY(6px); }
}
@keyframes webdev-reveal-5 {
    0%, 38%   { opacity: 0; transform: translateY(6px); }
    42%, 60%  { opacity: 1; transform: translateY(0); }
    72%, 100% { opacity: 0; transform: translateY(6px); }
}

/* ---------- Emblema "Online" (HTML, canto superior direito) ---------- */

.webdev-online-badge {
    position: absolute;
    top: 16px;
    right: 16px;
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 8px 14px 8px 10px;
    border-radius: 999px;
    border: 1px solid var(--color-border);
    background-color: rgba(10, 15, 26, 0.75);
    color: #5c6b84;
    box-shadow: 0 4px 16px rgba(0, 0, 0, 0.25);
    animation: webdev-badge-glow 9s linear infinite;
}

@keyframes webdev-badge-glow {
    0%, 40% {
        opacity: 0;
        transform: translateY(-4px);
        color: #5c6b84;
        border-color: var(--color-border);
        box-shadow: 0 4px 16px rgba(0, 0, 0, 0.25);
    }
    44%, 60% {
        opacity: 1;
        transform: translateY(0);
        color: #35d07f;
        border-color: #35d07f;
        box-shadow: 0 0 0 1px #35d07f, 0 4px 16px rgba(0, 0, 0, 0.25), 0 0 18px rgba(53, 208, 127, 0.5);
    }
    72%, 100% {
        opacity: 0;
        transform: translateY(-4px);
        color: #5c6b84;
        border-color: var(--color-border);
        box-shadow: 0 4px 16px rgba(0, 0, 0, 0.25);
    }
}

.webdev-online-icon {
    display: flex;
    width: 18px;
    height: 18px;
    flex-shrink: 0;
}

.webdev-online-icon svg {
    width: 100%;
    height: 100%;
}

.webdev-online-text {
    font-family: var(--font-mono);
    font-size: 11px;
    font-weight: bold;
    letter-spacing: 0.06em;
    white-space: nowrap;
}

@media (max-width: 700px) {
    .webdev-frame {
        padding: 14px;
    }

    .webdev-online-badge {
        padding: 6px 10px 6px 8px;
        gap: 6px;
    }

    .webdev-online-text {
        font-size: 9px;
    }

    .webdev-online-icon {
        width: 14px;
        height: 14px;
    }
}

/* ---------- Passo 4 "Testes" ----------
   Mesma consola de testes usada noutras páginas de serviço com um passo
   "Testes" (ver sistemas-seguranca.css), com os 4 tópicos próprios desta
   página (responsividade, navegadores, performance, acessibilidade).
   Cada linha tem uma janela de 16% do ciclo de 7s, seguida da anterior:
   anel a rodar (spinner) enquanto "a testar" e depois um visto verde
   quando aprovado, com uma barra de progresso geral a acompanhar. */
.process-test-panel {
    fill: var(--color-bg);
    stroke: var(--color-border);
    stroke-width: 3;
}

.process-test-label {
    font-size: 12px;
    fill: var(--color-text);
}

.process-test-ring {
    fill: none;
    stroke-width: 3;
}

.process-test-ring-1 { animation: process-test-ring-1 7s ease-in-out infinite; }
.process-test-ring-2 { animation: process-test-ring-2 7s ease-in-out infinite; }
.process-test-ring-3 { animation: process-test-ring-3 7s ease-in-out infinite; }
.process-test-ring-4 { animation: process-test-ring-4 7s ease-in-out infinite; }

@keyframes process-test-ring-1 { 0%, 11%  { stroke: var(--color-border); } 14%, 82% { stroke: #35d07f; } 92%, 100% { stroke: var(--color-border); } }
@keyframes process-test-ring-2 { 0%, 27%  { stroke: var(--color-border); } 30%, 82% { stroke: #35d07f; } 92%, 100% { stroke: var(--color-border); } }
@keyframes process-test-ring-3 { 0%, 43%  { stroke: var(--color-border); } 46%, 82% { stroke: #35d07f; } 92%, 100% { stroke: var(--color-border); } }
@keyframes process-test-ring-4 { 0%, 59%  { stroke: var(--color-border); } 62%, 82% { stroke: #35d07f; } 92%, 100% { stroke: var(--color-border); } }

.process-test-spinner {
    fill: none;
    stroke: var(--color-primary-light);
    stroke-width: 3;
    stroke-linecap: round;
    stroke-dasharray: 8 100;
    transform-box: fill-box;
    transform-origin: 50% 50%;
    animation: process-test-spin-rotate 0.8s linear infinite;
}

@keyframes process-test-spin-rotate {
    to { transform: rotate(360deg); }
}

.process-test-spin-1 { animation: process-test-spin-rotate 0.8s linear infinite, process-test-spin-show-1 7s linear infinite; }
.process-test-spin-2 { animation: process-test-spin-rotate 0.8s linear infinite, process-test-spin-show-2 7s linear infinite; }
.process-test-spin-3 { animation: process-test-spin-rotate 0.8s linear infinite, process-test-spin-show-3 7s linear infinite; }
.process-test-spin-4 { animation: process-test-spin-rotate 0.8s linear infinite, process-test-spin-show-4 7s linear infinite; }

@keyframes process-test-spin-show-1 { 0%, 2%  { opacity: 0; } 4%, 11%  { opacity: 1; } 13%, 100% { opacity: 0; } }
@keyframes process-test-spin-show-2 { 0%, 18% { opacity: 0; } 20%, 27% { opacity: 1; } 29%, 100% { opacity: 0; } }
@keyframes process-test-spin-show-3 { 0%, 34% { opacity: 0; } 36%, 43% { opacity: 1; } 45%, 100% { opacity: 0; } }
@keyframes process-test-spin-show-4 { 0%, 50% { opacity: 0; } 52%, 59% { opacity: 1; } 61%, 100% { opacity: 0; } }

.process-test-check {
    fill: none;
    stroke: #35d07f;
    stroke-width: 2.5;
    stroke-linecap: round;
    stroke-linejoin: round;
}

.process-test-check-1 { animation: process-test-check-show-1 7s linear infinite; }
.process-test-check-2 { animation: process-test-check-show-2 7s linear infinite; }
.process-test-check-3 { animation: process-test-check-show-3 7s linear infinite; }
.process-test-check-4 { animation: process-test-check-show-4 7s linear infinite; }

@keyframes process-test-check-show-1 { 0%, 13%  { opacity: 0; } 15%, 82% { opacity: 1; } 92%, 100% { opacity: 0; } }
@keyframes process-test-check-show-2 { 0%, 29%  { opacity: 0; } 31%, 82% { opacity: 1; } 92%, 100% { opacity: 0; } }
@keyframes process-test-check-show-3 { 0%, 45%  { opacity: 0; } 47%, 82% { opacity: 1; } 92%, 100% { opacity: 0; } }
@keyframes process-test-check-show-4 { 0%, 61%  { opacity: 0; } 63%, 82% { opacity: 1; } 92%, 100% { opacity: 0; } }

.process-test-bar-track {
    fill: var(--color-border);
}

.process-test-bar-fill {
    fill: #35d07f;
    transform-box: fill-box;
    transform-origin: 0% 50%;
    animation: process-test-bar-grow 7s ease-in-out infinite;
}

@keyframes process-test-bar-grow {
    0%, 2%    { transform: scaleX(0); }
    58%, 80%  { transform: scaleX(1); }
    90%, 100% { transform: scaleX(0); }
}

@media (prefers-reduced-motion: reduce) {
    .process-test-ring-1,
    .process-test-ring-2,
    .process-test-ring-3,
    .process-test-ring-4,
    .process-test-spinner,
    .process-test-spin-1,
    .process-test-spin-2,
    .process-test-spin-3,
    .process-test-spin-4,
    .process-test-check-1,
    .process-test-check-2,
    .process-test-check-3,
    .process-test-check-4,
    .process-test-bar-fill {
        animation: none;
    }

    .process-test-ring-1,
    .process-test-ring-2,
    .process-test-ring-3,
    .process-test-ring-4 {
        stroke: #35d07f;
    }

    .process-test-spinner {
        opacity: 0;
    }

    .process-test-check-1,
    .process-test-check-2,
    .process-test-check-3,
    .process-test-check-4 {
        opacity: 1;
    }

    .process-test-bar-fill {
        transform: scaleX(1);
    }
}

/* Animação exclusiva do passo 5 "Lançamento e manutenção": uma janela
   de navegador com o endereço a ser "escrito" letra a letra (mesma
   técnica do e-mail em solucoes-microsoft.css — um retângulo de recorte
   com "steps()" em vez de "scaleX" direto no texto, para não distorcer
   as letras). Duas fases alternam dentro da mesma janela: primeiro o
   conteúdo em "esqueleto" com uma barra "a publicar" a encher
   (".process-launch-publishing"); depois essa fase desaparece e entra
   o estado "Site no ar" (".process-launch-live"), com um gráfico de
   uptime em loop contínuo — o mesmo sinal de "serviço sempre
   monitorizado" já usado nas outras páginas de serviço. */
.process-launch-panel {
    fill: var(--color-bg);
    stroke: var(--color-border);
    stroke-width: 3;
}

.process-launch-titlebar {
    fill: var(--color-bg-alt);
}

.process-launch-urlbar {
    fill: var(--color-bg);
    stroke: var(--color-border);
    stroke-width: 1.5;
}

.process-launch-url-text {
    font-family: var(--font-mono);
    font-size: 9px;
    fill: var(--color-primary-light);
}

.process-launch-url-clip-rect {
    transform-box: fill-box;
    transform-origin: 0% 50%;
    animation: process-launch-type-url 8s linear infinite;
}

@keyframes process-launch-type-url {
    0%, 2%     { transform: scaleX(0); animation-timing-function: steps(8, jump-end); }
    18%        { transform: scaleX(1); }
    86%        { transform: scaleX(1); }
    94%, 100%  { transform: scaleX(0); }
}

.process-launch-publishing {
    animation: process-launch-publishing 8s ease-in-out infinite;
}

@keyframes process-launch-publishing {
    0%, 36%   { opacity: 1; }
    40%, 100% { opacity: 0; }
}

.process-launch-skeleton {
    fill: var(--color-border);
    animation: process-launch-shimmer 1.2s ease-in-out infinite;
}

@keyframes process-launch-shimmer {
    0%, 100% { opacity: 0.5; }
    50%      { opacity: 1; }
}

.process-launch-publish-label {
    font-size: 9px;
    fill: var(--color-text);
    opacity: 0.8;
}

.process-launch-progress-track {
    fill: var(--color-border);
}

.process-launch-progress-fill {
    fill: var(--color-primary-light);
    transform-box: fill-box;
    transform-origin: 0% 50%;
    animation: process-launch-progress-grow 8s ease-in-out infinite;
}

@keyframes process-launch-progress-grow {
    0%, 2%    { transform: scaleX(0); }
    34%, 36%  { transform: scaleX(1); }
    40%, 100% { transform: scaleX(0); }
}

.process-launch-live {
    animation: process-launch-live 8s ease-in-out infinite;
}

@keyframes process-launch-live {
    0%, 38%  { opacity: 0; }
    42%, 86% { opacity: 1; }
    90%, 100% { opacity: 0; }
}

.process-launch-dot {
    fill: #35d07f;
}

.process-launch-ping {
    fill: #35d07f;
    transform-box: fill-box;
    transform-origin: 50% 50%;
    animation: process-launch-ping 1.8s ease-out infinite;
}

@keyframes process-launch-ping {
    0%   { transform: scale(0.9); opacity: 0.6; }
    100% { transform: scale(2.4); opacity: 0; }
}

.process-launch-status {
    font-size: 11px;
    fill: var(--color-text);
}

.process-launch-leads-label {
    font-size: 10px;
    fill: var(--color-text);
    opacity: 0.7;
}

/* Lista de "leads a chegar" depois do site estar no ar: três cartões
   (pedido de orçamento, contacto, chamada) que entram um a seguir ao
   outro — deslizam ligeiramente da direita e aparecem em "fade", como
   notificações reais a chegar — ficam visíveis enquanto a fase
   ".process-launch-live" dura e desaparecem com ela no reset. Sem
   nenhum número inventado: o que comunica "há leads a entrar" é a
   própria chegada dos cartões, não uma contagem. */
.process-lead-card {
    fill: var(--color-bg-alt);
    stroke: var(--color-border);
    stroke-width: 2;
}

.process-lead-badge {
    fill: var(--color-primary);
    opacity: 0.12;
}

.process-lead-icon-shape {
    fill: none;
    stroke: var(--color-primary-light);
    stroke-width: 1.6;
    stroke-linecap: round;
    stroke-linejoin: round;
}

.process-lead-new-dot {
    fill: #35d07f;
}

.process-lead-text {
    font-size: 10px;
    fill: var(--color-text);
}

.process-lead-row {
    transform-box: fill-box;
    transform-origin: 50% 50%;
}

.process-lead-row-1 { animation: process-lead-row-1 8s ease-out infinite; }
.process-lead-row-2 { animation: process-lead-row-2 8s ease-out infinite; }
.process-lead-row-3 { animation: process-lead-row-3 8s ease-out infinite; }

@keyframes process-lead-row-1 {
    0%, 44%   { opacity: 0; transform: translateX(16px); }
    47%, 88%  { opacity: 1; transform: translateX(0); }
    92%, 100% { opacity: 0; transform: translateX(16px); }
}

@keyframes process-lead-row-2 {
    0%, 57%   { opacity: 0; transform: translateX(16px); }
    60%, 88%  { opacity: 1; transform: translateX(0); }
    92%, 100% { opacity: 0; transform: translateX(16px); }
}

@keyframes process-lead-row-3 {
    0%, 70%   { opacity: 0; transform: translateX(16px); }
    73%, 88%  { opacity: 1; transform: translateX(0); }
    92%, 100% { opacity: 0; transform: translateX(16px); }
}

@media (prefers-reduced-motion: reduce) {
    .process-launch-url-clip-rect,
    .process-launch-publishing,
    .process-launch-skeleton,
    .process-launch-progress-fill,
    .process-launch-live,
    .process-launch-ping,
    .process-lead-row-1,
    .process-lead-row-2,
    .process-lead-row-3 {
        animation: none;
    }

    .process-launch-url-clip-rect {
        transform: scaleX(1);
    }

    .process-launch-publishing {
        opacity: 0;
    }

    .process-launch-live {
        opacity: 1;
    }

    .process-launch-ping {
        opacity: 0;
    }

    .process-lead-row-1,
    .process-lead-row-2,
    .process-lead-row-3 {
        opacity: 1;
        transform: translateX(0);
    }
}
