/* ============================================================================
   HIỆU ỨNG & TƯƠNG TÁC — làm trang sinh động, "có phản hồi" với người dùng
   mà KHÔNG thay đổi thiết kế gốc.

   Nguyên tắc bắt buộc:
   1. Chỉ hoạt hình transform + opacity  -> mượt 60fps, không giật layout.
   2. Trạng thái ẩn chỉ áp dụng khi <html class="js-motion"> (JS chạy được)
      -> không có JavaScript thì nội dung vẫn hiện đầy đủ, không trang trắng.
   3. Tôn trọng prefers-reduced-motion: tắt sạch hiệu ứng.
   ========================================================================== */

/* ══ 1. THANH TIẾN TRÌNH CUỘN ═══════════════════════════════════════════════ */
.vh-progress {
  position: fixed; top: 0; left: 0; height: 3px; width: 100%;
  transform: scaleX(0); transform-origin: 0 50%;
  background: linear-gradient(90deg, var(--blue), var(--blue-2), var(--amber));
  z-index: 200; pointer-events: none;
  transition: opacity .3s ease;
}

/* ══ 2. HIỆN DẦN KHI CUỘN TỚI ══════════════════════════════════════════════ */
.js-motion [data-reveal] {
  opacity: 0;
  transform: translateY(20px);
  will-change: opacity, transform;
}
.js-motion [data-reveal].is-in { will-change: auto }
.js-motion [data-reveal].is-in {
  opacity: 1; transform: none;
  transition: opacity .66s cubic-bezier(.22, .61, .36, 1) var(--rd, 0ms),
              transform .66s cubic-bezier(.22, .61, .36, 1) var(--rd, 0ms);
}
.js-motion [data-reveal="left"]  { transform: translateX(-24px) }
.js-motion [data-reveal="right"] { transform: translateX(24px) }
.js-motion [data-reveal="zoom"]  { transform: scale(.955) }
.js-motion [data-reveal="rise"]  { transform: translateY(38px) scale(.98) }
/* Trên màn hình hẹp, hiệu ứng trượt NGANG làm trang bị tràn ngang trước khi
   phần tử hiện ra -> đổi sang trượt DỌC cho mọi kiểu. */
@media (max-width: 900px) {
  .js-motion [data-reveal="left"],
  .js-motion [data-reveal="right"] { transform: translateY(20px) }
}

/* ══ 3. THẺ CÓ CHIỀU SÂU — nghiêng 3D + vệt sáng theo con trỏ ══════════════ */
.tilt { transform-style: preserve-3d }
.js-motion [data-reveal].tilt, .tilt { transition: transform .5s cubic-bezier(.22,.61,.36,1), box-shadow .35s ease }
.js-motion [data-reveal].tilt.is-tilting, .tilt.is-tilting { transition: transform .08s linear, box-shadow .35s ease }
/* Vệt sáng chạy theo con trỏ (đặt dưới nội dung, không chặn click) */
.spot { position: relative; isolation: isolate }
.spot::before {
  content: ""; position: absolute; inset: 0; z-index: 0;
  border-radius: inherit; opacity: 0; transition: opacity .35s ease;
  background: radial-gradient(320px circle at var(--mx, 50%) var(--my, 50%),
              rgba(51, 70, 221, .10), transparent 62%);
}
.spot:hover::before { opacity: 1 }
.spot > * { position: relative; z-index: 1 }

/* ══ 4. NÚT — nam châm nhẹ + gợn sóng khi bấm ══════════════════════════════ */
.btn { position: relative; overflow: hidden }
.btn:active { transform: translateY(1px) scale(.985) }
.ripple {
  position: absolute; border-radius: 50%; pointer-events: none;
  background: rgba(255, 255, 255, .55); transform: scale(0); opacity: .7;
  animation: vhRipple .62s cubic-bezier(.22, .61, .36, 1) forwards;
}
.btn-outline .ripple, .btn-ghost .ripple, .btn-white .ripple {
  background: rgba(51, 70, 221, .22);
}
@keyframes vhRipple { to { transform: scale(2.6); opacity: 0 } }

/* ══ 5. THANH ĐIỀU HƯỚNG ═══════════════════════════════════════════════════ */
header.nav { transition: box-shadow .28s ease, background-color .28s ease }
header.nav.is-stuck {
  box-shadow: 0 8px 28px -14px rgba(15, 23, 42, .3);
  background: rgba(255, 255, 255, .97);
}
header.nav .container { transition: height .28s ease }
header.nav.is-stuck .container { height: 58px }

nav.primary a { position: relative }
nav.primary a::after {
  content: ""; position: absolute; left: 13px; right: 13px; bottom: 4px; height: 2px;
  background: var(--blue); border-radius: 2px;
  transform: scaleX(0); transform-origin: left; transition: transform .26s ease;
}
nav.primary a:hover::after, nav.primary a.is-current::after { transform: scaleX(1) }
nav.primary a.active::after { transform: scaleX(1); opacity: .45 }

/* ══ 6. THẺ SẢN PHẨM / TIN / VIỆC LÀM ══════════════════════════════════════ */
.device, .listcard, .job, .reg, .svc, .channels a {
  transition: transform .24s cubic-bezier(.22, .61, .36, 1),
              box-shadow .24s ease, border-color .24s ease;
}
.device .img, .listcard .thumb, .pd-gallery { overflow: hidden }
.device .img img, .listcard .thumb img {
  transition: transform .5s cubic-bezier(.22, .61, .36, 1);
}
.device:hover .img img, .listcard:hover .thumb img { transform: scale(1.05) }

/* ══ 7. SỐ LIỆU ĐẾM LÊN ════════════════════════════════════════════════════ */
[data-count] { font-variant-numeric: tabular-nums }

/* ══ 8. CHẤM "ĐANG HOẠT ĐỘNG" ══════════════════════════════════════════════ */
.utility .left .dot { animation: vhPulse 2.4s ease-in-out infinite }
@keyframes vhPulse {
  0%, 100% { box-shadow: 0 0 0 0 rgba(5, 150, 105, .55) }
  50%      { box-shadow: 0 0 0 5px rgba(5, 150, 105, 0) }
}

/* ══ 9. HERO — nền trôi rất chậm + thẻ nổi bồng bềnh ═══════════════════════ */
.hero { background-size: 160% 160%, auto; animation: vhDrift 28s ease-in-out infinite alternate }
@keyframes vhDrift {
  from { background-position: 82% 12%, 0 0 }
  to   { background-position: 62% 26%, 0 0 }
}
.float-stat { animation: vhFloat 7s ease-in-out infinite }
.float-stat.f2 { animation-delay: -3.5s }
@keyframes vhFloat {
  0%, 100% { transform: translateY(0) }
  50%      { transform: translateY(-9px) }
}

/* ══ 10. BẢNG ĐIỀU HÀNH MÔ PHỎNG — "sống" như thật ═════════════════════════ */
/* Xe chạy dọc theo tuyến đường trong bản đồ mô phỏng */
/* Không dùng nền/khung nữa: bản thân chiếc xe đã là hình nhiều màu.
   margin âm = nửa kích thước -> tâm xe nằm ĐÚNG toạ độ trên tuyến đường. */
.dash-truck {
  position: absolute; width: 30px; height: 22px; margin: -11px 0 0 -15px;
  z-index: 3; display: grid; place-items: center;
  filter: drop-shadow(0 2px 3px rgba(15, 23, 42, .45));
  transition: none;
}
.dash-truck svg { width: 30px; height: 22px; display: block }
/* Quầng sáng TRÒN lan ra từ xe — như đang phát tín hiệu về trung tâm.
   Dùng box-shadow tròn thay vì khung vuông phóng to: khung vuông chụp ở bất kỳ
   khoảnh khắc nào cũng giống một "cái hộp" bao quanh xe bị thu nhỏ. */
.dash-truck::after {
  content: ""; position: absolute; left: 50%; top: 50%;
  width: 20px; height: 20px; margin: -10px 0 0 -10px; border-radius: 50%;
  box-shadow: 0 0 0 0 rgba(51, 70, 221, .4);
  animation: vhTruckPing 2s ease-out infinite;
}
@keyframes vhTruckPing {
  70%  { box-shadow: 0 0 0 11px rgba(51, 70, 221, 0) }
  100% { box-shadow: 0 0 0 0 rgba(51, 70, 221, 0) }
}
/* Vệt đã đi qua sáng dần */
.dash-trail { transition: stroke-dashoffset .1s linear }
/* Cảnh báo trượt vào */
.dash-toast {
  position: absolute; right: 8px; top: 8px; z-index: 4;
  background: #fff; border: 1px solid var(--line); border-radius: 8px;
  padding: 6px 10px; font-size: 10px; font-weight: 600; color: var(--ink);
  box-shadow: 0 8px 18px -8px rgba(15, 23, 42, .3);
  display: flex; align-items: center; gap: 6px;
  transform: translateY(-14px); opacity: 0;
  transition: transform .4s cubic-bezier(.22, .61, .36, 1), opacity .4s ease;
  max-width: 62%;
}
.dash-toast.on { transform: none; opacity: 1 }
.dash-toast i { width: 6px; height: 6px; border-radius: 50%; background: var(--green); flex: none }
.dash-toast.warn i { background: var(--amber) }
/* Số KPI trong bảng điều hành nhấp nháy khi đổi giá trị */
.dash-kpi b { transition: color .3s ease }
.dash-kpi b.bump { animation: vhBump .5s ease }
@keyframes vhBump {
  0% { transform: translateY(0) }
  35% { transform: translateY(-3px); color: var(--blue) }
  100% { transform: translateY(0) }
}

/* ══ 11. DÒNG THỜI GIAN 2002 → NAY ═════════════════════════════════════════ */
.tl-wrap { padding: 78px 0; background: var(--paper-2); border-bottom: 1px solid var(--line) }
.tl { position: relative; margin-top: 40px; padding-left: 30px }
/* Đường kẻ nền + đường tiến trình chạy theo cuộn */
.tl::before {
  content: ""; position: absolute; left: 7px; top: 6px; bottom: 6px; width: 2px;
  background: var(--line-2); border-radius: 2px;
}
.tl-fill {
  position: absolute; left: 7px; top: 6px; bottom: 6px; width: 2px; border-radius: 2px;
  transform: scaleY(0); transform-origin: top;
  background: linear-gradient(180deg, var(--blue), var(--blue-2));
  box-shadow: 0 0 10px -1px rgba(51, 70, 221, .55);
}
.tl-item { position: relative; padding: 0 0 30px 26px }
.tl-item:last-child { padding-bottom: 0 }
.tl-item::before {
  content: ""; position: absolute; left: -30px; top: 4px;
  width: 16px; height: 16px; border-radius: 50%;
  background: #fff; border: 3px solid var(--line-2);
  transition: border-color .45s ease, transform .45s cubic-bezier(.34, 1.56, .64, 1),
              box-shadow .45s ease;
}
.tl-item.lit::before {
  border-color: var(--blue); transform: scale(1.22);
  box-shadow: 0 0 0 5px rgba(51, 70, 221, .12);
}
.tl-year {
  font-family: "JetBrains Mono", ui-monospace, monospace;
  font-size: 17px; font-weight: 500; letter-spacing: .02em; color: var(--blue);
  display: block; line-height: 1.1;
}
.tl-item h3 { margin: 6px 0 4px; font-size: 16px; font-weight: 700; letter-spacing: -.015em }
.tl-item p { margin: 0; font-size: 13.5px; line-height: 1.6; color: var(--mute); max-width: 62ch }
.tl-badge {
  display: inline-block; margin-top: 7px; font-size: 10.5px; font-weight: 700;
  letter-spacing: .04em; text-transform: uppercase;
  padding: 3px 9px; border-radius: 999px;
  background: var(--blue-soft); color: var(--blue-deep);
}
.tl-badge.gold { background: #FEF3C7; color: #92400E }
@media (min-width: 900px) {
  .tl { padding-left: 0; margin-left: 50%; transform: translateX(-1px) }
  .tl::before, .tl-fill { left: -1px }
  .tl-item { width: 100%; padding-left: 34px }
  .tl-item::before { left: -10px }
  .tl-item:nth-child(even) {
    margin-left: -100%; padding-left: 0; padding-right: 34px; text-align: right;
  }
  .tl-item:nth-child(even)::before { left: auto; right: -10px }
  .tl-item:nth-child(even) p { margin-left: auto }
}

/* ══ 12. DẢI KHÁCH HÀNG CHẠY NGANG ═════════════════════════════════════════ */
.trust { padding: 30px 0; background: #fff; border-bottom: 1px solid var(--line); overflow: hidden }
.trust-lab {
  text-align: center; font-family: "JetBrains Mono", monospace; font-size: 11px;
  text-transform: uppercase; letter-spacing: .1em; color: var(--mute); margin-bottom: 18px;
}
.marquee { position: relative; display: flex; overflow: hidden; -webkit-mask-image: linear-gradient(90deg, transparent, #000 8%, #000 92%, transparent); mask-image: linear-gradient(90deg, transparent, #000 8%, #000 92%, transparent) }
.marquee-row { display: flex; flex: none; gap: 14px; padding-right: 14px; animation: vhMarquee 42s linear infinite }
.marquee:hover .marquee-row,
.marquee.paused .marquee-row { animation-play-state: paused }
.marquee-pause {
  margin-left: 10px; font: inherit; font-size: 10.5px; font-weight: 600;
  color: var(--mute); background: transparent; border: 1px solid var(--line-2);
  border-radius: 999px; padding: 2px 10px; cursor: pointer;
  text-transform: none; letter-spacing: 0; vertical-align: middle;
}
.marquee-pause:hover { border-color: var(--blue); color: var(--blue) }
@keyframes vhMarquee { to { transform: translateX(-100%) } }
.chip-client {
  flex: none; display: inline-flex; align-items: center; gap: 8px;
  padding: 9px 16px; border: 1px solid var(--line); border-radius: 999px;
  background: var(--paper-2); font-size: 13.5px; font-weight: 600; color: var(--ink-3);
  white-space: nowrap; transition: border-color .2s ease, color .2s ease, background-color .2s ease;
}
.chip-client:hover { border-color: var(--blue); color: var(--blue-deep); background: var(--blue-soft) }
.chip-client small {
  font-family: "JetBrains Mono", monospace; font-size: 11px;
  color: var(--mute); font-weight: 500;
}

/* ══ 12b. NÚT CHAT ZALO NỔI — sống động, không phải icon tĩnh ═══════════════
   Nút tròn Zalo ở góc phải dưới: có vòng sóng lan toả + nhún nhẹ định kỳ, rê
   chuột thì phóng to, và một bong bóng chào tự hiện sau vài giây (đóng được,
   nhớ trong phiên). Render sẵn ở máy chủ nên không JS vẫn bấm chat được. */
.vh-zalo { position: fixed; right: 22px; bottom: 24px; z-index: 96; }

.vh-zalo-btn {
  position: relative; display: grid; place-items: center;
  width: 58px; height: 58px; border-radius: 50%;
  background: #0068FF; color: #fff; text-decoration: none;
  box-shadow: 0 12px 26px -8px rgba(0, 104, 255, .65);
  animation: vhZaloBob 4.2s ease-in-out infinite;
  transition: transform .25s cubic-bezier(.34, 1.56, .64, 1), box-shadow .25s ease;
}
.vh-zalo-btn:hover { transform: scale(1.08); box-shadow: 0 16px 32px -8px rgba(0, 104, 255, .75); animation-play-state: paused; }
.vh-zalo-btn:active { transform: scale(.98); }
.vh-zalo-mark { width: 34px; height: 34px; position: relative; z-index: 2; }
/* Hai vòng sóng lan ra — cảm giác "đang online, bấm để chat" */
.vh-zalo-btn::before, .vh-zalo-btn::after {
  content: ""; position: absolute; inset: 0; border-radius: 50%;
  background: rgba(0, 104, 255, .45); z-index: 1;
  animation: vhZaloPulse 2.6s cubic-bezier(.4, 0, .2, 1) infinite;
}
.vh-zalo-btn::after { animation-delay: 1.3s; }
@keyframes vhZaloPulse { 0% { transform: scale(1); opacity: .6 } 80%, 100% { transform: scale(1.75); opacity: 0 } }
/* Nhún + lắc nhẹ mỗi chu kỳ để "bắt mắt" mà không rối */
@keyframes vhZaloBob {
  0%, 82%, 100% { transform: translateY(0) rotate(0) }
  86% { transform: translateY(-5px) rotate(-9deg) }
  90% { transform: translateY(-5px) rotate(9deg) }
  94% { transform: translateY(-2px) rotate(-5deg) }
}
/* Huy hiệu "1" tin nhắn chờ — tăng cảm giác tương tác */
.vh-zalo-badge {
  position: absolute; top: -3px; right: -3px; z-index: 3;
  min-width: 19px; height: 19px; padding: 0 5px; border-radius: 999px;
  background: #F5333F; color: #fff; font-size: 11px; font-weight: 800; line-height: 19px;
  text-align: center; box-shadow: 0 0 0 2px #fff;
}

/* Bong bóng chào */
.vh-zalo-pop {
  position: absolute; right: 4px; bottom: 74px; width: 250px;
  background: #fff; color: var(--ink); border: 1px solid var(--line); border-radius: 16px;
  padding: 15px 16px 15px; box-shadow: 0 18px 42px -16px rgba(15, 23, 42, .5);
  transform-origin: bottom right; transform: translateY(12px) scale(.94);
  opacity: 0; visibility: hidden; pointer-events: none;
  transition: opacity .3s ease, transform .34s cubic-bezier(.34, 1.56, .64, 1), visibility .34s;
}
/* Đã đóng (bấm ×) thì KHÔNG hiện lại kể cả khi đang rê chuột — nếu không, con
   trỏ nằm trên bong bóng lúc bấm × vẫn giữ :hover -> bong bóng bật lại ngay,
   khiến nút × "bấm không đóng được". */
.vh-zalo:not(.user-closed):hover .vh-zalo-pop, .vh-zalo.pop-on:not(.user-closed) .vh-zalo-pop {
  opacity: 1; visibility: visible; pointer-events: auto; transform: none;
}
.vh-zalo-pop::after {   /* mũi nhọn chỉ xuống nút */
  content: ""; position: absolute; right: 24px; bottom: -7px; width: 14px; height: 14px;
  background: #fff; border-right: 1px solid var(--line); border-bottom: 1px solid var(--line);
  transform: rotate(45deg);
}
.vh-zalo-pop b { display: block; font-size: 14px; letter-spacing: -.01em; margin-right: 34px; }
.vh-zalo-pop span { display: block; font-size: 12px; color: var(--mute); line-height: 1.45; margin-top: 4px; }
.vh-zalo-cta {
  display: inline-block; margin-top: 10px; font-size: 12.5px; font-weight: 700;
  color: #0068FF; text-decoration: none;
}
.vh-zalo-cta:hover { text-decoration: underline; }
.vh-zalo-cta .arr { transition: transform .2s ease; display: inline-block; }
.vh-zalo-cta:hover .arr { transform: translateX(3px); }
.vh-zalo-x {
  position: absolute; top: 6px; right: 6px; z-index: 2; width: 30px; height: 30px; border: 0;
  background: var(--paper-2, #eef1f8); color: var(--ink); font-size: 21px; line-height: 30px;
  text-align: center; cursor: pointer; padding: 0;
  border-radius: 50%; transition: background-color .2s ease, color .2s ease, transform .15s ease;
}
.vh-zalo-x:hover { background: #F5333F; color: #fff; }
.vh-zalo-x:active { transform: scale(.9); }
.vh-zalo-btn:focus-visible, .vh-zalo-x:focus-visible, .vh-zalo-cta:focus-visible {
  outline: 3px solid #0068FF; outline-offset: 3px; border-radius: 10px;
}
/* Điện thoại: nâng lên trên thanh hành động cố định (.vh-bar ở đáy) */
@media (max-width: 720px) {
  .vh-zalo { right: 14px; bottom: 82px; }
  .vh-zalo-btn { width: 52px; height: 52px; }
  .vh-zalo-mark { width: 30px; height: 30px; }
  .vh-zalo-pop { width: 224px; }
}

/* ══ 13. NÚT LÊN ĐẦU TRANG ═════════════════════════════════════════════════ */
.to-top {
  position: fixed; right: 24px; bottom: 92px; z-index: 90;
  width: 44px; height: 44px; border-radius: 50%; border: 1px solid var(--line);
  background: #fff; color: var(--blue); display: grid; place-items: center;
  box-shadow: 0 10px 24px -10px rgba(15, 23, 42, .32); cursor: pointer;
  opacity: 0; transform: translateY(14px) scale(.9); pointer-events: none;
  visibility: hidden;
  transition: opacity .3s ease, transform .3s cubic-bezier(.34, 1.56, .64, 1),
              background-color .2s ease, color .2s ease, visibility .3s;
}
.to-top.on { opacity: 1; transform: none; pointer-events: auto; visibility: visible }
.to-top:hover { background: var(--blue); color: #fff; border-color: var(--blue) }
.to-top svg { width: 18px; height: 18px }
/* Chua cho nut mot khoang rieng de khong che dong ban quyen o chan trang.
   Có thêm nút Zalo (luôn hiện) + nút lên đầu trang xếp chồng nên chừa cao hơn. */
footer .bottom { padding-bottom: 96px }
@media (max-width: 720px) { footer .bottom { padding-bottom: 150px } }
@media (min-width: 1500px) { footer .bottom { padding-bottom: 20px } }

/* ══ 14. VIỀN TIÊU ĐIỂM KHI DÙNG BÀN PHÍM ══════════════════════════════════
   Chỉ hiện khi điều hướng bằng phím Tab (không hiện khi bấm chuột). */
.to-top:focus-visible,
.device:focus-visible, .listcard:focus-visible, .job:focus-visible,
.btn:focus-visible, nav.primary a:focus-visible, .chip-client:focus-visible {
  outline: 3px solid var(--blue);
  outline-offset: 3px;
  border-radius: 10px;
}
/* Thẻ nghiêng 3D: khi lấy tiêu điểm bằng bàn phím thì trả về thẳng cho dễ đọc */
.tilt:focus-visible { transform: none !important }

/* ══ 15. ẢNH TẢI XONG THÌ HIỆN MỀM ═════════════════════════════════════════ */
.js-motion img[loading="lazy"] { opacity: 0; transition: opacity .5s ease }
.js-motion img[loading="lazy"].ready,
.js-motion img[loading="lazy"].is-in { opacity: 1 }

/* ══ 16. THÔNG BÁO NHỎ (sao chép, lỗi biểu mẫu…) ═══════════════════════════ */
.vh-toast {
  position: fixed; left: 50%; bottom: 26px; transform: translate(-50%, 16px);
  z-index: 210; background: var(--ink); color: #fff;
  font-size: 13.5px; font-weight: 600; padding: 11px 18px; border-radius: 999px;
  box-shadow: 0 14px 34px -12px rgba(11, 16, 32, .55);
  opacity: 0; pointer-events: none; visibility: hidden; max-width: 90vw;
  transition: opacity .25s ease, transform .25s cubic-bezier(.34, 1.56, .64, 1), visibility .25s;
}
.vh-toast.on { opacity: 1; transform: translate(-50%, 0); visibility: visible }

/* ══ 17. THANH HÀNH ĐỘNG CỐ ĐỊNH (điện thoại) ══════════════════════════════ */
.vh-bar { display: none }
@media (max-width: 720px) {
  .vh-bar {
    display: flex; gap: 10px; position: fixed; left: 12px; right: 12px; bottom: 12px;
    z-index: 95; transform: translateY(130%); visibility: hidden;
    transition: transform .32s cubic-bezier(.22, .61, .36, 1), visibility .32s;
  }
  .vh-bar.on { transform: none; visibility: visible }
  .vh-bar .b {
    flex: 1; display: inline-flex; align-items: center; justify-content: center; gap: 7px;
    padding: 14px 12px; border-radius: 12px; font-size: 14.5px; font-weight: 700;
    box-shadow: 0 10px 26px -10px rgba(11, 16, 32, .4);
  }
  .vh-bar .b svg { width: 17px; height: 17px }
  .vh-bar .call { background: #fff; color: var(--blue-deep); border: 1px solid var(--line-2) }
  .vh-bar .quote { background: var(--blue); color: #fff }
  /* Nút lên đầu trang xếp TRÊN nút Zalo (Zalo ở bottom:82, cao 52) */
  .to-top { bottom: 146px }
  /* Thông báo nhỏ phải nổi CAO HƠN thanh hành động, nếu không sẽ bị che */
  .vh-toast { bottom: 84px }
}

/* ══ 18. BỘ LỌC DANH MỤC (trang Sản phẩm) ══════════════════════════════════ */
.vh-filter { display: flex; flex-wrap: wrap; gap: 8px; margin-top: 20px }
.vh-filter button {
  font: inherit; font-size: 13px; font-weight: 600; color: var(--ink-3);
  background: #fff; border: 1px solid var(--line-2); border-radius: 999px;
  padding: 8px 15px; cursor: pointer;
  transition: background-color .18s ease, border-color .18s ease, color .18s ease, transform .18s ease;
}
.vh-filter button:hover { border-color: var(--blue); color: var(--blue) }
.vh-filter button.on { background: var(--blue); border-color: var(--blue); color: #fff }
.vh-filter button:active { transform: translateY(1px) }
/* Khi lọc, nhóm đầu tiên đang hiện không cần đường kẻ ngăn cách phía trên */
.prod-group.vh-first { border-top: 0 !important; margin-top: 0 !important; padding-top: 0 !important }

/* ══ 18b. NÚT CHUYỂN NGỮ VI / EN ══════════════════════════════════════════ */
.lang-sw {
  display: inline-flex; align-items: center; justify-content: center;
  min-width: 38px; height: 34px; padding: 0 10px; border-radius: 8px;
  border: 1px solid var(--line-2); background: #fff;
  font-size: 12.5px; font-weight: 700; letter-spacing: .04em; color: var(--ink-3);
  transition: border-color .18s ease, color .18s ease, background-color .18s ease;
}
.lang-sw:hover { border-color: var(--blue); color: var(--blue); background: var(--blue-soft) }
.lang-sw:focus-visible { outline: 3px solid var(--blue); outline-offset: 2px }
@media (max-width: 1000px) and (min-width: 681px) { .lang-sw { min-width: 34px; height: 31px; font-size: 12px } }

/* ══ 19. XEM ẢNH PHÓNG TO ══════════════════════════════════════════════════ */
.vh-lb {
  position: fixed; inset: 0; z-index: 220; display: none;
  align-items: center; justify-content: center; padding: 40px 20px;
  background: rgba(11, 16, 32, .88); backdrop-filter: blur(3px);
}
.vh-lb.on { display: flex }
.vh-lb figure { margin: 0; max-width: 100%; max-height: 100%; text-align: center }
.vh-lb img {
  max-width: min(1100px, 92vw); max-height: 78vh; width: auto; height: auto;
  border-radius: 12px; background: #fff; box-shadow: 0 30px 70px -20px rgba(0, 0, 0, .7);
  animation: vhLbIn .28s cubic-bezier(.22, .61, .36, 1);
}
@keyframes vhLbIn { from { transform: scale(.96); opacity: 0 } to { transform: none; opacity: 1 } }
.vh-lb figcaption {
  margin-top: 14px; color: #CFD3E8; font-size: 13.5px; font-weight: 500;
  max-width: 70ch; margin-left: auto; margin-right: auto;
}
.vh-lb-x {
  position: absolute; top: 16px; right: 18px; width: 40px; height: 40px;
  border-radius: 50%; border: 1px solid rgba(255, 255, 255, .25);
  background: rgba(255, 255, 255, .1); color: #fff; font-size: 17px; cursor: pointer;
  transition: background-color .18s ease;
}
.vh-lb-x:hover { background: rgba(255, 255, 255, .22) }
.vh-lb-nav {
  position: absolute; top: 50%; transform: translateY(-50%);
  width: 46px; height: 66px; border: 0; border-radius: 10px;
  background: rgba(255, 255, 255, .1); color: #fff; font-size: 30px; line-height: 1;
  cursor: pointer; display: none; transition: background-color .18s ease;
}
.vh-lb.multi .vh-lb-nav { display: block }
.vh-lb-nav:hover { background: rgba(255, 255, 255, .22) }
.vh-lb-nav.prev { left: 14px }
.vh-lb-nav.next { right: 14px }
.vh-lb-x:focus-visible, .vh-lb-nav:focus-visible { outline: 3px solid #fff; outline-offset: 2px }
@media (max-width: 640px) {
  .vh-lb-nav { width: 38px; height: 54px; font-size: 24px }
  .vh-lb img { max-height: 68vh }
}

/* ══ 20. VÙNG SÁNG BÁM CON TRỎ Ở ĐẦU TRANG ════════════════════════════════ */
.hero::before {
  content: ""; position: absolute; inset: 0; pointer-events: none; z-index: 0;
  background: radial-gradient(420px circle at var(--hx, 78%) var(--hy, 18%),
              rgba(51, 70, 221, .07), transparent 70%);
  opacity: 0; transition: opacity .45s ease;
}
.hero:hover::before { opacity: 1 }
.hero > * { position: relative; z-index: 1 }

/* ══ 21. HÀNH TRÌNH DẪN ĐƯỜNG — kể chuyện theo thao tác cuộn ═══════════════
   Thanh dọc mảnh ở mép trái: chiếc xe "chạy" xuống theo trang, đường sáng dần
   và mỗi chặng bật sáng đúng lúc phần nội dung tương ứng vào giữa màn hình.
   Là LỚP PHỦ cộng thêm — nằm gọn trong lề trái (dưới 28px padding), không có
   JS thì không dựng ra nên trang không bị ảnh hưởng. Chỉ hiện trên màn rộng.
   Chú thích (.cap) là tooltip nổi: chỉ hiện khi rê/chọn, được phép phủ lên
   mép nội dung như mọi tooltip. */
/* top: max(...) để LUÔN nằm dưới header cố định (~102px) — trên màn hình thấp
   (cao 640–750px) mà chỉ dùng 15vh thì xe/quầng nhô lên đè vào header. */
.vh-journey { position: fixed; left: 0; top: max(15vh, 124px); bottom: 12vh; width: 250px;
  z-index: 55; pointer-events: none; display: none; }
.vh-journey.on { display: block; }
.vh-journey-track { position: absolute; left: 14px; top: 0; bottom: 0; width: 3px; }
.vh-journey-road { position: absolute; inset: 0; border-radius: 3px; background: rgba(51, 70, 221, .13); }
.vh-journey-fill { position: absolute; left: 0; top: 0; width: 100%; height: 0;
  border-radius: 3px; background: linear-gradient(180deg, var(--blue), var(--blue-2));
  transition: height .5s cubic-bezier(.22, .61, .36, 1); }

.vh-stop { position: absolute; left: 1.5px; transform: translate(-50%, -50%);
  width: 24px; height: 24px; padding: 0; margin: 0; border: 0; background: transparent;
  -webkit-appearance: none; appearance: none; pointer-events: auto; cursor: pointer; z-index: 3; }
.vh-stop .dot { position: absolute; left: 50%; top: 50%; transform: translate(-50%, -50%);
  width: 11px; height: 11px; border-radius: 50%; background: #fff;
  /* .75 alpha -> ~3.6:1 với nền trắng, đạt WCAG 1.4.11 cho phần tử tương tác */
  border: 2px solid rgba(51, 70, 221, .75);
  transition: background-color .3s ease, border-color .3s ease, transform .3s ease, box-shadow .3s ease; }
.vh-stop.done .dot { background: var(--blue); border-color: var(--blue); }
.vh-stop.current .dot { transform: translate(-50%, -50%) scale(1.18); box-shadow: 0 0 0 5px rgba(51, 70, 221, .15); }
.vh-stop:focus-visible { outline: none; }
.vh-stop:focus-visible .dot { box-shadow: 0 0 0 4px rgba(51, 70, 221, .4); }

/* visibility:hidden khi ẩn -> KHÔNG bắt sự kiện chuột (nội dung bên dưới vẫn
   bấm được) dù pointer-events:auto khi hiện. Cho phép rê chuột LÊN chú thích để
   đọc (WCAG 1.4.13 "hoverable") — .cap:hover giữ nó mở; nút và chú thích chồng
   nhẹ ở mép nên con trỏ đi liền mạch được. */
.vh-stop .cap { position: absolute; left: 22px; top: 50%; transform: translate(-8px, -50%);
  width: max-content; max-width: 220px; opacity: 0; visibility: hidden; pointer-events: none;
  background: #fff; color: var(--ink); border: 1px solid var(--line); border-radius: 12px;
  padding: 9px 13px; box-shadow: 0 16px 36px -18px rgba(15, 23, 42, .5);
  transition: opacity .22s ease, transform .22s ease, visibility .22s ease; }
.vh-stop .cap b { display: block; font-size: 12.5px; font-weight: 700; letter-spacing: -.01em; white-space: nowrap; }
.vh-stop .cap b i { font-style: normal; color: var(--blue); margin-right: 6px; }
.vh-stop .cap span { display: block; font-size: 11px; color: var(--mute); margin-top: 3px; line-height: 1.4; white-space: normal; }
.vh-stop:hover .cap, .vh-stop:focus-visible .cap, .vh-stop .cap:hover {
  opacity: 1; visibility: visible; pointer-events: auto; transform: translate(0, -50%); }
/* Esc để tắt chú thích mà KHÔNG dời tiêu điểm (WCAG 1.4.13 "dismissible") */
.vh-journey.vh-hush .vh-stop .cap { opacity: 0 !important; visibility: hidden !important; pointer-events: none !important; }

.vh-truck { position: absolute; left: 1.5px; top: 0; transform: translate(-50%, -50%);
  width: 22px; height: 22px; border-radius: 50%; background: #fff; border: 1.5px solid var(--blue);
  display: grid; place-items: center; z-index: 2; box-shadow: 0 4px 12px -3px rgba(51, 70, 221, .55);
  transition: top .5s cubic-bezier(.22, .61, .36, 1); }
.vh-truck svg { width: 14px; height: 10px; display: block; }
.vh-truck::after { content: ""; position: absolute; left: 50%; top: 50%; width: 22px; height: 22px;
  margin: -11px 0 0 -11px; border-radius: 50%; box-shadow: 0 0 0 0 rgba(51, 70, 221, .4);
  animation: vhTruckPing 2s ease-out infinite; }

/* Chỉ hiện khi màn hình đủ rộng & đủ cao — dưới ngưỡng này ẩn hẳn để không
   chồng lên nội dung ở lề hẹp (JS cũng chỉ bật lớp .on khi khớp điều kiện). */
@media (max-width: 1279px), (max-height: 639px) {
  .vh-journey { display: none !important; }
}

/* ══ TÔN TRỌNG "GIẢM CHUYỂN ĐỘNG" — tắt toàn bộ ═══════════════════════════ */
@media (prefers-reduced-motion: reduce) {
  .js-motion [data-reveal] { opacity: 1 !important; transform: none !important; transition: none !important }
  .js-motion img[loading="lazy"] { opacity: 1 !important; transition: none }
  .hero, .float-stat, .utility .left .dot { animation: none }
  /* Dung chay -> phai cho xuong dong, neu khong se mat khach hang cuoi danh sach */
  .marquee { -webkit-mask-image: none; mask-image: none; overflow: visible }
  .marquee-row { animation: none; flex-wrap: wrap; justify-content: center; padding-right: 0 }
  .marquee-row + .marquee-row { display: none }
  .marquee-pause { display: none }
  .vh-toast, .vh-bar { transition: none }
  .vh-lb img { animation: none }
  .hero::before { display: none }
  .tilt, .device .img img, .listcard .thumb img,
  header.nav, header.nav .container, nav.primary a::after,
  .btn, .to-top, .dash-toast, .tl-item::before { transition: none !important }
  .device:hover .img img, .listcard:hover .thumb img { transform: none }
  .spot::before { display: none }
  .ripple { display: none }
  .dash-truck { display: none }
  .dash-truck::after { animation: none }
  /* Nút Zalo: vẫn hiện & bấm được, chỉ tắt vòng sóng + nhún + hoạt hình bong bóng */
  .vh-zalo-btn { animation: none }
  .vh-zalo-btn::before, .vh-zalo-btn::after { animation: none; display: none }
  .vh-zalo-pop { transition: none }
  /* Hành trình dẫn đường: giữ lại như thanh điều hướng tĩnh (bấm để tới phần),
     nhưng tắt quầng nhấp nháy và mọi chuyển động của xe. */
  .vh-truck::after { animation: none }
  .vh-truck, .vh-journey-fill { transition: none }
  .vh-stop .dot, .vh-stop.current .dot { transition: none }
  .vh-progress { display: none }
  .tl-fill { height: 100% !important }
  .tl-item::before { border-color: var(--blue) }
}
