/* Hub and spokes: integration layer, links, packets and exchange log (includes/visuals/hub.php) */
.hb-svg { max-width: 1120px; margin-inline: auto; }
.hb-link { fill: none; stroke: var(--forest); stroke-width: 2.2; stroke-linecap: round; }
.hb-link--sched { stroke: #7d8a80; stroke-dasharray: 8 7; }
.hb-pk { fill: none; stroke-width: 13; stroke-linecap: round; stroke-dasharray: .1 99.9; opacity: 0; }
.hb-pk--out { stroke: var(--green-2); }
.hb-pk--in { stroke: var(--forest); }
.hb-lt { font-size: 18px; font-style: italic; fill: var(--ink-2); paint-order: stroke; stroke: var(--paper); stroke-width: 8px; stroke-linejoin: round; }
.section--paper .hb-lt { stroke: var(--white); }
.hb-box { fill: var(--white); stroke: var(--line); stroke-width: 1.5; }
.section--paper .hb-box { fill: var(--paper); }
.hb-name { fill: var(--forest); font-size: 26px; font-weight: 700; }
.hb-sub { fill: var(--ink-2); font-size: 18px; }
.hb-core { fill: var(--forest); }
.hb-halo { fill: var(--green); opacity: 0; }
.hb-cname { fill: var(--white); font-size: 25px; font-weight: 700; }
.hb-csub { fill: var(--green); font-size: 16.5px; font-weight: 600; }
.hb-key { width: 12px; height: 12px; border-radius: 50%; flex: none; }
.hb-key--in { background: var(--forest); }
.hb-key--out { background: var(--green-2); }
.hb-legend { justify-content: center; margin-top: 10px; }

/* the list replaces the drawing on phones; kept for screen readers elsewhere */
.hb-list, .hb-center-m { position: absolute; width: 1px; height: 1px; margin: -1px; padding: 0; overflow: hidden; clip: rect(0, 0, 0, 0); white-space: nowrap; border: 0; }

/* exchange log */
.hb-log { margin-top: 28px; border-radius: 12px; background: var(--forest); color: var(--white); overflow: hidden; }
.hb-log-t { display: flex; align-items: center; gap: 10px; margin: 0; padding: 12px 20px; border-bottom: 1px solid rgba(255, 255, 255, .12);
  font-size: 12.5px; font-weight: 600; letter-spacing: .08em; text-transform: uppercase; color: var(--green); }
.hb-led { width: 8px; height: 8px; border-radius: 50%; background: var(--green); box-shadow: 0 0 0 4px rgba(150, 248, 120, .18); }
.hb-lines { list-style: none; margin: 0; padding: 14px 20px 16px; display: grid; gap: 7px; font-family: ui-monospace, "SFMono-Regular", Menlo, Consolas, monospace; font-size: 13.5px; line-height: 1.45; }
.hb-l { display: grid; grid-template-columns: auto 76px minmax(0, 1fr); gap: 4px 16px; align-items: baseline; }
.hb-time { color: rgba(255, 255, 255, .7); font-variant-numeric: tabular-nums; }
.hb-st { justify-self: start; padding: 0 7px; border-radius: 4px; font-size: 12px; font-weight: 700; letter-spacing: .04em; }
.hb-st--ok { color: var(--green); box-shadow: 0 0 0 1px rgba(150, 248, 120, .45) inset; }
.hb-st--warn { background: var(--white); color: var(--forest); }
.hb-st--retry { background: var(--green); color: var(--forest); }
.hb-msg { color: rgba(255, 255, 255, .92); }

/* intro: hub, links, systems, labels; then packets flow and the log fills line by line */
.js .vz-figure .hb-hub { opacity: 0; transform: scale(.85); transform-box: fill-box; transform-origin: center; transition: opacity .5s ease .1s, transform .6s cubic-bezier(.2, .7, .2, 1) .1s; }
.js .vz-figure .hb-link { opacity: 0; transition: opacity .6s ease .5s; }
.js .vz-figure .hb-node { opacity: 0; transform: scale(.9); transform-box: fill-box; transform-origin: center; transition: opacity .5s ease, transform .5s cubic-bezier(.2, .7, .2, 1); }
.js .vz-figure .hb-node.hb-d1 { transition-delay: .6s; } .js .vz-figure .hb-node.hb-d4 { transition-delay: .7s; }
.js .vz-figure .hb-node.hb-d2 { transition-delay: .8s; } .js .vz-figure .hb-node.hb-d5 { transition-delay: .9s; }
.js .vz-figure .hb-node.hb-d3 { transition-delay: 1s; } .js .vz-figure .hb-node.hb-d6 { transition-delay: 1.1s; }
.js .vz-figure .hb-lt { opacity: 0; transition: opacity .6s ease 1.3s; }
.js .vz-figure .hb-l { opacity: 0; transform: translateY(6px); transition: opacity .4s ease, transform .4s ease; }
.js .vz-figure .hb-l1 { transition-delay: 1.5s; } .js .vz-figure .hb-l2 { transition-delay: 1.85s; } .js .vz-figure .hb-l3 { transition-delay: 2.2s; }
.js .vz-figure .hb-l4 { transition-delay: 2.55s; } .js .vz-figure .hb-l5 { transition-delay: 2.9s; } .js .vz-figure .hb-l6 { transition-delay: 3.25s; }
.js .vz-figure.is-visible .hb-hub, .js .vz-figure.is-visible .hb-node, .js .vz-figure.is-visible .hb-l { opacity: 1; transform: none; }
.js .vz-figure.is-visible .hb-link, .js .vz-figure.is-visible .hb-lt { opacity: 1; }
.js .vz-figure.is-visible .hb-halo { animation: hb-halo 3s ease-in-out 1.5s infinite; transform-box: fill-box; transform-origin: center; }
.js .vz-figure.is-visible .hb-led { animation: hb-led 1.6s ease-in-out 1.5s infinite; }
.js .vz-figure.is-visible .hb-pk--out { animation: hb-out 3.2s linear infinite; }
.js .vz-figure.is-visible .hb-pk--in { animation: hb-in 3.2s linear infinite; }
.js .vz-figure.is-visible .hb-pk.hb-d1 { animation-delay: 1.6s; } .js .vz-figure.is-visible .hb-pk--in.hb-d1 { animation-delay: 3.2s; }
.js .vz-figure.is-visible .hb-pk.hb-d2 { animation-delay: 2.1s; } .js .vz-figure.is-visible .hb-pk--in.hb-d2 { animation-delay: 1.8s; }
.js .vz-figure.is-visible .hb-pk.hb-d3 { animation-delay: 2.4s; }
.js .vz-figure.is-visible .hb-pk.hb-d4 { animation-delay: 2.7s; } .js .vz-figure.is-visible .hb-pk--in.hb-d4 { animation-delay: 1.9s; }
.js .vz-figure.is-visible .hb-pk.hb-d5 { animation-delay: 2.9s; }
.js .vz-figure.is-visible .hb-pk.hb-d6 { animation-delay: 3.4s; }
@keyframes hb-out { 0% { stroke-dashoffset: 0; opacity: 0; } 8%, 84% { opacity: 1; } 92%, 100% { stroke-dashoffset: -100; opacity: 0; } }
@keyframes hb-in { 0% { stroke-dashoffset: 0; opacity: 0; } 8%, 84% { opacity: 1; } 92%, 100% { stroke-dashoffset: 100; opacity: 0; } }
@keyframes hb-halo { 0%, 100% { opacity: 0; transform: scale(.96); } 50% { opacity: .3; transform: scale(1.08); } }
@keyframes hb-led { 50% { opacity: .35; } }

@media (max-width: 760px) {
  .hb-svg, .hb-legend { display: none; }
  .hb-list, .hb-center-m { position: static; width: auto; height: auto; margin: 0; overflow: visible; clip: auto; white-space: normal; }
  .hb-center-m { padding: 16px 18px; border-radius: 12px; background: var(--forest); color: var(--green); font-size: 13.5px; font-weight: 600; text-align: center; }
  .hb-center-m span { display: block; margin-bottom: 2px; font-family: var(--font-serif); font-size: 21px; font-weight: 500; color: var(--white); }
  .hb-list { list-style: none; padding: 0; margin-top: 12px; display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 8px; position: relative; }
  .hb-li { display: flex; flex-direction: column; gap: 2px; padding: 12px 12px 12px 14px; border-radius: 10px; background: var(--white); border-left: 3px solid var(--forest); }
  .hb-li--sched { border-left: 3px dashed #7d8a80; }
  .hb-li-name { font-weight: 700; font-size: 15.5px; color: var(--forest); }
  .hb-li-sub { font-size: 13px; color: var(--ink-2); }
  .hb-li-link { margin-top: 6px; font-size: 13px; font-style: italic; color: var(--ink); }
  .hb-li-g { display: inline-block; margin-right: 5px; font-style: normal; font-weight: 700; color: var(--green-text); }
  .hb-log { margin-top: 18px; }
  .hb-lines { padding: 12px 14px 14px; font-size: 12.5px; gap: 10px; }
  .hb-l { grid-template-columns: auto minmax(0, 1fr); gap: 2px 10px; }
  .hb-msg { grid-column: 1 / -1; }
  .js .vz-figure .hb-li { opacity: 0; transform: translateY(8px); transition: opacity .4s ease, transform .4s ease; }
  .js .vz-figure .hb-li:nth-child(2) { transition-delay: .1s; } .js .vz-figure .hb-li:nth-child(3) { transition-delay: .2s; }
  .js .vz-figure .hb-li:nth-child(4) { transition-delay: .3s; } .js .vz-figure .hb-li:nth-child(5) { transition-delay: .4s; }
  .js .vz-figure .hb-li:nth-child(6) { transition-delay: .5s; }
  .js .vz-figure.is-visible .hb-li { opacity: 1; transform: none; }
}
