The Real One


<html class="scroll-smooth" lang="en">
 |  <head>
 |  <meta charset="utf-8"/>
 |  <meta content="width=device-width, initial-scale=1" name="viewport"/>
 |  <title>
 |  Smart Sphere Star Harnessing App
 |  </title>
 |  <script src="https://cdn.tailwindcss.com">
|  </script>
|  <link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.3/css/all.min.css" rel="stylesheet"/>
|  <link href="https://fonts.googleapis.com/css2?family=Orbitron&amp;family=Roboto+Mono&amp;display=swap" rel="stylesheet"/>
|  <style>
|  body {
|  font-family: 'Roboto Mono', monospace;
|  background-color: #0f172a;
|  color: #d1d5db;
|  }
|  .terminal {
|  background-color: #111827;
|  border-radius: 0.5rem;
|  box-shadow: 0 0 15px #22c55e;
|  font-family: 'Roboto Mono', monospace;
|  font-size: 0.875rem;
|  line-height: 1.25rem;
|  color: #22c55e;
|  padding: 1rem;
|  min-height: 300px;
|  overflow-y: auto;
|  white-space: pre-wrap;
|  user-select: text;
|  }
|  .terminal-input {
|  outline: none;
|  border: none;
|  background: transparent;
|  color: #22c55e;
|  font-family: 'Roboto Mono', monospace;
|  font-size: 0.875rem;
|  width: 100%;
|  caret-color: #22c55e;
|  }
|  .scrollbar-thin::-webkit-scrollbar {
|  width: 6px;
|  }
|  .scrollbar-thin::-webkit-scrollbar-track {
|  background: transparent;
|  }
|  .scrollbar-thin::-webkit-scrollbar-thumb {
|  background-color: #22c55e;
|  border-radius: 3px;
|  }
|  .star-filled-vial {
|  width: 48px;
|  height: 96px;
|  background: linear-gradient(180deg, #22c55e 0%, #166534 100%);
|  border-radius: 0.75rem 0.75rem 0.25rem 0.25rem;
|  box-shadow: 0 0 8px #22c55e;
|  position: relative;
|  margin: 0.25rem;
|  display: flex;
|  flex-direction: column;
|  justify-content: flex-end;
|  overflow: hidden;
|  cursor: grab;
|  transition: transform 0.3s ease;
|  }
|  .star-filled-vial:active {
|  cursor: grabbing;
|  transform: scale(1.1);
|  box-shadow: 0 0 20px #4ade80;
|  z-index: 1000;
|  }
|  .star-filled-vial:hover {
|  transform: scale(1.1);
|  box-shadow: 0 0 15px #4ade80;
|  z-index: 10;
|  }
|  .star-filled-vial::before {
|  content: '';
|  position: absolute;
|  top: 0.25rem;
|  left: 50%;
|  transform: translateX(-50%);
|  width: 24px;
|  height: 12px;
|  background: #166534;
|  border-radius: 12px 12px 0 0;
|  box-shadow: inset 0 2px 4px #22c55e;
|  z-index: 10;
|  }
|  .vial-liquid {
|  background: #22c55e;
|  height: 60%;
|  border-radius: 0 0 0.75rem 0.75rem;
|  box-shadow: inset 0 0 10px #4ade80;
|  transition: height 0.5s ease;
|  }
|  .btn-green {
|  background-color: #22c55e;
|  color: #0f172a;
|  font-weight: 600;
|  transition: background-color 0.3s ease;
|  }
|  .btn-green:hover:not(:disabled) {
|  background-color: #16a34a;
|  }
|  .btn-green:disabled {
|  background-color: #4ade80;
|  cursor: not-allowed;
|  }
|  .btn-red {
|  background-color: #dc2626;
|  color: #fef2f2;
|  font-weight: 600;
|  transition: background-color 0.3s ease;
|  }
|  .btn-red:hover:not(:disabled) {
|  background-color: #b91c1c;
|  }
|  .btn-red:disabled {
|  background-color: #fca5a5;
|  cursor: not-allowed;
|  }
|  .btn-yellow {
|  background-color: #eab308;
|  color: #1e293b;
|  font-weight: 600;
|  transition: background-color 0.3s ease;
|  }
|  .btn-yellow:hover {
|  background-color: #ca8a04;
|  }
|  .scrollbar-thin {
|  scrollbar-width: thin;
|  scrollbar-color: #22c55e transparent;
|  }
|  /* Sphere container and beams animation */
|  .sphere-container {
|  position: relative;
|  width: 100%;
|  max-width: 400px;
|  aspect-ratio: 1 / 1;
|  margin: 0 auto;
|  perspective: 1200px;
|  }
|  .sphere {
|  width: 100%;
|  height: 100%;
|  border-radius: 50%;
|  background: radial-gradient(circle at center, #22c55e 20%, #064e3b 90%);
|  box-shadow:
|  inset 0 0 20px #4ade80,
|  0 0 30px #22c55e;
|  position: relative;
|  transform-style: preserve-3d;
|  animation: sphere-rotate 20s linear infinite;
|  }
|  @keyframes sphere-rotate {
|  0% {
|  transform: rotateX(0deg) rotateY(0deg);
|  }
|  100% {
|  transform: rotateX(360deg) rotateY(360deg);
|  }
|  }
|  /* Beams container */
|  .beams-container {
|  position: absolute;
|  top: 50%;
|  left: 50%;
|  width: 100%;
|  height: 100%;
|  pointer-events: none;
|  transform-style: preserve-3d;
|  transform-origin: center center;
|  animation: beams-pulse 3s ease-in-out infinite;
|  }
|  @keyframes beams-pulse {
|  0%, 100% {
|  filter: drop-shadow(0 0 6px #22c55e);
|  }
|  50% {
|  filter: drop-shadow(0 0 12px #4ade80);
|  }
|  }
|  /* Beam line */
|  .beam-line {
|  position: absolute;
|  width: 2px;
|  background: linear-gradient(180deg, #22c55e, transparent);
|  border-radius: 1px;
|  transform-origin: top center;
|  animation: beam-glow 2s ease-in-out infinite alternate;
|  filter: drop-shadow(0 0 4px #22c55e);
|  }
|  @keyframes beam-glow {
|  0% {
|  opacity: 0.6;
|  box-shadow: 0 0 6px #22c55e;
|  }
|  100% {
|  opacity: 1;
|  box-shadow: 0 0 14px #4ade80;
|  }
|  }
|  /* Star dot */
|  .star-dot {
|  position: absolute;
|  width: 12px;
|  height: 12px;
|  background: #22c55e;
|  border-radius: 50%;
|  box-shadow: 0 0 8px #4ade80;
|  cursor: pointer;
|  transition: transform 0.3s ease;
|  }
|  .star-dot:hover {
|  transform: scale(1.5);
|  box-shadow: 0 0 20px #86efac;
|  z-index: 20;
|  }
|  /* Voice & Brain info box */
|  .info-box {
|  background: #064e3b;
|  border: 2px solid #22c55e;
|  border-radius: 0.5rem;
|  padding: 1rem;
|  margin-top: 1rem;
|  color: #a7f3d0;
|  font-size: 0.9rem;
|  font-family: 'Roboto Mono', monospace;
|  user-select: none;
|  }
|  /* Voice icon animation */
|  .voice-icon {
|  animation: pulse-voice 2s infinite;
|  color: #22c55e;
|  font-size: 1.5rem;
|  vertical-align: middle;
|  margin-right: 0.5rem;
|  }
|  @keyframes pulse-voice {
|  0%, 100% {
|  opacity: 1;
|  text-shadow: 0 0 6px #22c55e;
|  }
|  50% {
|  opacity: 0.6;
|  text-shadow: 0 0 12px #4ade80;
|  }
|  }
|  /* Brain icon animation */
|  .brain-icon {
|  animation: pulse-brain 3s infinite;
|  color: #22c55e;
|  font-size: 1.5rem;
|  vertical-align: middle;
|  margin-right: 0.5rem;
|  }
|  @keyframes pulse-brain {
|  0%, 100% {
|  opacity: 1;
|  text-shadow: 0 0 6px #22c55e;
|  }
|  50% {
|  opacity: 0.7;
|  text-shadow: 0 0 14px #4ade80;
|  }
|  }
|  /* Scrollable star list with custom scrollbar */
|  .star-list {
|  max-height: 180px;
|  overflow-y: auto;
|  scrollbar-width: thin;
|  scrollbar-color: #22c55e transparent;
|  }
|  .star-list::-webkit-scrollbar {
|  width: 6px;
|  }
|  .star-list::-webkit-scrollbar-track {
|  background: transparent;
|  }
|  .star-list::-webkit-scrollbar-thumb {
|  background-color: #22c55e;
|  border-radius: 3px;
|  }
|  /* Tooltip for star dots */
|  .tooltip {
|  position: absolute;
|  background: #064e3b;
|  border: 1px solid #22c55e;
|  padding: 0.25rem 0.5rem;
|  border-radius: 0.25rem;
|  font-size: 0.75rem;
|  color: #a7f3d0;
|  pointer-events: none;
|  white-space: nowrap;
|  user-select: none;
|  z-index: 50;
|  opacity: 0;
|  transition: opacity 0.2s ease;
|  }
|  .tooltip.visible {
|  opacity: 1;
|  }
|  /* Drag & Drop container styles */
|  #vials-container, #distribution-container {
|  min-height: 120px;
|  border: 2px dashed #22c55e;
|  border-radius: 0.5rem;
|  padding: 0.5rem;
|  display: flex;
|  flex-wrap: wrap;
|  gap: 0.5rem;
|  background-color: #0f172a;
|  transition: background-color 0.3s ease;
|  }
|  #vials-container.dragover, #distribution-container.dragover {
|  background-color: #164e2e;
|  border-color: #4ade80;
|  }
|  /* Distribution section */
|  #distribution-section {
|  background-color: #111827;
|  border-radius: 0.75rem;
|  padding: 1rem;
|  margin-top: 1rem;
|  color: #a7f3d0;
|  font-family: 'Roboto Mono', monospace;
|  }
|  #distribution-section h3 {
|  font-family: 'Orbitron', monospace;
|  color: #22c55e;
|  margin-bottom: 0.5rem;
|  }
|  /* Timezone grid */
|  #timezone-grid {
|  display: grid;
|  grid-template-columns: repeat(auto-fill,minmax(120px,1fr));
|  gap: 0.5rem;
|  max-height: 300px;
|  overflow-y: auto;
|  border: 1px solid #22c55e;
|  border-radius: 0.5rem;
|  padding: 0.5rem;
|  background-color: #0f172a;
|  }
|  .timezone-block {
|  background-color: #064e3b;
|  border: 1px solid #22c55e;
|  border-radius: 0.5rem;
|  padding: 0.5rem;
|  font-size: 0.75rem;
|  text-align: center;
|  user-select: none;
|  cursor: default;
|  color: #a7f3d0;
|  display: flex;
|  flex-direction: column;
|  justify-content: center;
|  align-items: center;
|  min-height: 60px;
|  transition: background-color 0.3s ease;
|  }
|  .timezone-block.active {
|  background-color: #22c55e;
|  color: #0f172a;
|  font-weight: 700;
|  box-shadow: 0 0 10px #4ade80;
|  }
|  /* Responsive tweaks */
|  @media (max-width: 768px) {
|  main {
|  grid-template-columns: 1fr !important;
|  }
|  #distribution-section {
|  margin-top: 1.5rem;
|  }
|  }
|  </style>
|  </head>
|  <body class="min-h-screen flex flex-col">
|  <header class="bg-gray-900 p-4 flex flex-col md:flex-row items-center justify-between">
|  <div class="flex items-center space-x-3">
|  <img alt="Smart tracking sphere, metallic silver with green glowing lines, floating in space" class="w-12 h-12 rounded-full" src="https://placehold.co/48x48/png?text=Sphere"/>
|  <h1 class="text-2xl font-orbitron font-bold text-green-400 select-none">
|  Smart Sphere Star Harnessing
|  </h1>
|  </div>
|  <nav class="mt-3 md:mt-0">
|  <ul class="flex space-x-6 text-green-300 font-semibold text-sm select-none">
|  <li>
|  <button aria-label="Start harnessing process" class="btn-green px-3 py-1 rounded flex items-center space-x-2" id="btn-start">
|  <i aria-hidden="true" class="fas fa-play">
|  </i>
|  <span>
|  Start Harness
|  </span>
|  </button>
|  </li>
|  <li>
|  <button aria-label="Stop harnessing process" class="btn-red px-3 py-1 rounded flex items-center space-x-2" disabled="" id="btn-stop">
|  <i aria-hidden="true" class="fas fa-stop">
|  </i>
|  <span>
|  Stop Harness
|  </span>
|  </button>
|  </li>
|  </ul>
|  </nav>
|  </header>
|  <main class="flex-grow p-4 max-w-7xl mx-auto grid grid-cols-1 md:grid-cols-4 gap-6">
|  <!-- Sphere & Beams Section -->
|  <section class="col-span-1 md:col-span-2 bg-gray-800 rounded-lg p-4 flex flex-col items-center relative">
|  <div aria-label="Smart sphere with tracking beams" class="sphere-container">
|  <div class="sphere" id="sphere">
|  </div>
|  <div aria-hidden="true" class="beams-container" id="beams-container">
|  </div>
|  <div aria-hidden="true" class="tooltip" id="tooltip" role="tooltip">
|  </div>
|  </div>
|  <p class="mt-4 text-green-300 text-center font-mono text-sm max-w-xl">
|  The sphere intelligently tracks stars and harnesses their energy by searching constellations and individual stars. Click on stars to see details.
|  </p>
|  <div aria-atomic="true" aria-live="polite" class="info-box mt-6 w-full max-w-xl" id="voice-brain-info">
|  <div class="flex items-center mb-2">
|  <i aria-hidden="true" class="fas fa-microphone voice-icon">
|  </i>
|  <span>
|  <strong>
|  Voice Enabled:
|  </strong>
|  The sphere can communicate with stars using voice commands.
|  </span>
|  </div>
|  <div class="flex items-center">
|  <i aria-hidden="true" class="fas fa-brain brain-icon">
|  </i>
|  <span>
|  <strong>
|  Brain Insurance:
|  </strong>
|  Only
|  <em>
|  Antonio Rodriguez Jr.
|  </em>
|  can convert, channel, stream, listen, touch, smell, feel, and manage star energy.
|  </span>
|  </div>
|  </div>
|  </section>
|  <!-- Star List & Vials Section -->
|  <section class="col-span-1 md:col-span-2 bg-gray-900 rounded-lg p-4 flex flex-col">
|  <h2 class="text-green-400 font-orbitron text-xl mb-3 select-none">
|  Stars Harnessed &amp; To Harness
|  </h2>
|  <div class="flex flex-col space-y-4 overflow-y-auto max-h-[400px] scrollbar-thin pr-2">
|  <div>
|  <h3 class="text-green-300 font-semibold mb-1">
|  Harnessed Stars
|  </h3>
|  <ul aria-label="List of harnessed stars" class="list-disc list-inside text-green-200 star-list" id="list-harnessed" tabindex="0">
|  </ul>
|  </div>
|  <div>
|  <h3 class="text-yellow-400 font-semibold mb-1">
|  Stars To Harness
|  </h3>
|  <ul aria-label="List of stars to harness" class="list-disc list-inside text-yellow-300 star-list" id="list-to-harness" tabindex="0">
|  </ul>
|  </div>
|  </div>
|  <h2 class="text-green-400 font-orbitron text-xl mt-6 mb-3 select-none">
|  Collected Vials (Drag to Distribute Energy)
|  </h2>
|  <div aria-dropeffect="move" aria-label="Collected energy vials" class="flex flex-wrap gap-2 min-h-[120px]" id="vials-container" tabindex="0">
|  </div>
|  <section aria-label="Energy distribution section" id="distribution-section" tabindex="0">
|  <h3>
|  Energy Distribution Across Timezones
|  </h3>
|  <p class="mb-2 text-sm text-green-300">
|  Drag vials here to distribute star energy to real-life locations worldwide using IP blocks and timezone coverage. All timezones are included to ensure universal interest reception.
|  </p>
|  <div aria-dropeffect="move" aria-label="Distributed energy vials container" class="min-h-[120px] flex flex-wrap gap-2" id="distribution-container" tabindex="0">
|  </div>
|  <h3 class="mt-4">
|  Timezones
|  </h3>
|  <div aria-label="List of all world timezones with energy distribution status" id="timezone-grid" tabindex="0">
|  </div>
|  </section>
|  </section>
|  </main>
|  <!-- Terminal Section -->
|  <section class="bg-gray-900 p-4 max-w-7xl mx-auto rounded-lg mt-6 mb-6">
|  <h2 class="text-green-400 font-orbitron text-xl mb-3 select-none">
|  Star Communication Terminal
|  </h2>
|  <div aria-atomic="true" aria-label="Star communication terminal" aria-live="polite" aria-multiline="true" class="terminal scrollbar-thin" contenteditable="false" id="terminal" role="textbox" tabindex="0">
|  <div aria-atomic="true" aria-live="polite" class="mb-2" id="terminal-output">
|  </div>
|  <div class="flex items-center space-x-2">
|  <span aria-hidden="true" class="text-green-400 font-bold select-none">
|  &gt;
|  </span>
|  <input aria-label="Terminal command input" autocomplete="off" class="terminal-input flex-grow" disabled="" id="terminal-input" spellcheck="false" type="text"/>
|  </div>
|  </div>
|  </section>
|  <script>
|  // Data for stars with 3D positions (x,y in % relative to sphere container)
|  const allStars = [
|  { name: "Sirius", constellation: "Canis Major", harnessed: true, x: 70, y: 30, voice: true, brain: true },
|  { name: "Betelgeuse", constellation: "Orion", harnessed: true, x: 40, y: 20, voice: true, brain: false },
|  { name: "Rigel", constellation: "Orion", harnessed: false, x: 45, y: 60, voice: false, brain: false },
|  { name: "Vega", constellation: "Lyra", harnessed: false, x: 80, y: 50, voice: false, brain: false },
|  { name: "Polaris", constellation: "Ursa Minor", harnessed: true, x: 50, y: 10, voice: true, brain: true },
|  { name: "Altair", constellation: "Aquila", harnessed: false, x: 60, y: 70, voice: false, brain: false },
|  { name: "Aldebaran", constellation: "Taurus", harnessed: false, x: 30, y: 40, voice: false, brain: false },
|  { name: "Antares", constellation: "Scorpius", harnessed: false, x: 20, y: 65, voice: false, brain: false },
|  { name: "Spica", constellation: "Virgo", harnessed: true, x: 35, y: 25, voice: true, brain: false },
|  { name: "Deneb", constellation: "Cygnus", harnessed: false, x: 75, y: 75, voice: false, brain: false },
|  { name: "Castor", constellation: "Gemini", harnessed: false, x: 55, y: 35, voice: false, brain: false },
|  { name: "Pollux", constellation: "Gemini", harnessed: false, x: 58, y: 38, voice: false, brain: false },
|  { name: "Procyon", constellation: "Canis Minor", harnessed: true, x: 65, y: 45, voice: true, brain: false },
|  { name: "Fomalhaut", constellation: "Piscis Austrinus", harnessed: false, x: 25, y: 55, voice: false, brain: false },
|  { name: "Regulus", constellation: "Leo", harnessed: false, x: 40, y: 75, voice: false, brain: false }
|  ];
|

|  // List of all timezones (IANA) with display names and UTC offsets
|  // For brevity, a representative subset of all timezones is included here.
|  // In a real app, you would include all timezones.
|  const timezones = [
|  { id: "Pacific/Midway", name: "Midway Island", offset: "-11:00" },
|  { id: "Pacific/Honolulu", name: "Hawaii", offset: "-10:00" },
|  { id: "America/Anchorage", name: "Alaska", offset: "-09:00" },
|  { id: "America/Los_Angeles", name: "Pacific Time (US & Canada)", offset: "-08:00" },
|  { id: "America/Denver", name: "Mountain Time (US & Canada)", offset: "-07:00" },
|  { id: "America/Chicago", name: "Central Time (US & Canada)", offset: "-06:00" },
|  { id: "America/New_York", name: "Eastern Time (US & Canada)", offset: "-05:00" },
|  { id: "America/Caracas", name: "Caracas", offset: "-04:30" },
|  { id: "America/Halifax", name: "Atlantic Time (Canada)", offset: "-04:00" },
|  { id: "America/St_Johns", name: "Newfoundland", offset: "-03:30" },
|  { id: "America/Argentina/Buenos_Aires", name: "Buenos Aires", offset: "-03:00" },
|  { id: "Atlantic/South_Georgia", name: "South Georgia", offset: "-02:00" },
|  { id: "Atlantic/Azores", name: "Azores", offset: "-01:00" },
|  { id: "Europe/London", name: "London", offset: "+00:00" },
|  { id: "Europe/Berlin", name: "Berlin", offset: "+01:00" },
|  { id: "Europe/Athens", name: "Athens", offset: "+02:00" },
|  { id: "Europe/Moscow", name: "Moscow", offset: "+03:00" },
|  { id: "Asia/Dubai", name: "Dubai", offset: "+04:00" },
|  { id: "Asia/Karachi", name: "Karachi", offset: "+05:00" },
|  { id: "Asia/Kolkata", name: "India Standard Time", offset: "+05:30" },
|  { id: "Asia/Bangkok", name: "Bangkok", offset: "+07:00" },
|  { id: "Asia/Shanghai", name: "Shanghai", offset: "+08:00" },
|  { id: "Asia/Tokyo", name: "Tokyo", offset: "+09:00" },
|  { id: "Australia/Sydney", name: "Sydney", offset: "+10:00" },
|  { id: "Pacific/Auckland", name: "Auckland", offset: "+12:00" },
|  { id: "Pacific/Chatham", name: "Chatham Islands", offset: "+12:45" }
|  ];
|

|  // Commands for terminal
|  const commands = {
|  help: {
|  description: "List available commands",
|  action: () => {
|  return Object.entries(commands)
|  .map(([cmd, obj]) => `${cmd} - ${obj.description}`)
|  .join("\n");
|  },
|  },
|  list: {
|  description: "List stars and their harness status",
|  action: () => {
|  let output = "Harnessed Stars:\n";
|  output += allStars.filter(s => s.harnessed).map(s => `- ${s.name} (${s.constellation})`).join("\n") + "\n\n";
|  output += "Stars To Harness:\n";
|  output += allStars.filter(s => !s.harnessed).map(s => `- ${s.name} (${s.constellation})`).join("\n");
|  return output;
|  },
|  },
|  harness: {
|  description: "Start harnessing a star by name. Usage: harness [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  if (star.harnessed) return `Star '${star.name}' is already harnessed.`;
|  star.harnessed = true;
|  updateStarLists();
|  addVial(star.name);
|  updateStarDot(star.name);
|  return `Star '${star.name}' is now harnessed and energy vial collected.`;
|  },
|  },
|  unharness: {
|  description: "Remove harness from a star by name. Usage: unharness [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  if (!star.harnessed) return `Star '${star.name}' is not harnessed.`;
|  star.harnessed = false;
|  updateStarLists();
|  removeVial(star.name);
|  updateStarDot(star.name);
|  return `Star '${star.name}' harness removed and vial discarded.`;
|  },
|  },
|  tasks: {
|  description: "List tasks due for harnessing and energy management",
|  action: () => {
|  const toHarness = allStars.filter(s => !s.harnessed);
|  if (!toHarness.length) return "All stars are harnessed. No pending tasks.";
|  return toHarness.map(s => `- Harness star '${s.name}' in constellation '${s.constellation}'`).join("\n");
|  },
|  },
|  status: {
|  description: "Show current harnessing status",
|  action: () => {
|  const harnessedCount = allStars.filter(s => s.harnessed).length;
|  const total = allStars.length;
|  return `Harnessed ${harnessedCount} out of ${total} stars.\nVials collected: ${vials.length}`;
|  },
|  },
|  clear: {
|  description: "Clear terminal output",
|  action: () => {
|  terminalOutput.innerText = "";
|  return "";
|  },
|  },
|  voice: {
|  description: "Toggle voice communication with a star. Usage: voice [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  star.voice = !star.voice;
|  updateStarDot(star.name);
|  return `Voice communication ${star.voice ? "enabled" : "disabled"} for star '${star.name}'.`;
|  }
|  },
|  brain: {
|  description: "Toggle brain insurance for a star. Usage: brain [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  if (currentUser !== "Antonio Rodriguez Jr.") return "Access denied: Only Antonio Rodriguez Jr. can toggle brain insurance.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  star.brain = !star.brain;
|  updateStarDot(star.name);
|  return `Brain insurance ${star.brain ? "enabled" : "disabled"} for star '${star.name}'.`;
|  }
|  }
|  };
|

|  // Vials collected
|  let vials = [];
|

|  // Distributed vials mapped by timezone id
|  let distributedVials = {};
|

|  // DOM references
|  const listHarnessed = document.getElementById("list-harnessed");
|  const listToHarness = document.getElementById("list-to-harness");
|  const vialsContainer = document.getElementById("vials-container");
|  const distributionContainer = document.getElementById("distribution-container");
|  const timezoneGrid = document.getElementById("timezone-grid");
|  const btnStart = document.getElementById("btn-start");
|  const btnStop = document.getElementById("btn-stop");
|  const terminal = document.getElementById("terminal");
|  const terminalOutput = document.getElementById("terminal-output");
|  const terminalInput = document.getElementById("terminal-input");
|  const beamsContainer = document.getElementById("beams-container");
|  const sphere = document.getElementById("sphere");
|  const tooltip = document.getElementById("tooltip");
|  const voiceBrainInfo = document.getElementById("voice-brain-info");
|

|  // Animation and harnessing state
|  let harnessing = false;
|  let harnessInterval = null;
|  let currentHarnessIndex = 0;
|

|  // Antonio Rodriguez Jr. special user check (simulate)
|  const currentUser = "Antonio Rodriguez Jr.";
|

|  // Initialize star lists
|  function updateStarLists() {
|  listHarnessed.innerHTML = "";
|  listToHarness.innerHTML = "";
|  allStars.forEach((star) => {
|  const li = document.createElement("li");
|  li.textContent = `${star.name} (${star.constellation})`;
|  if (star.harnessed) {
|  listHarnessed.appendChild(li);
|  } else {
|  listToHarness.appendChild(li);
|  }
|  });
|  }
|

|  // Add vial for star
|  function addVial(starName) {
|  if (!vials.includes(starName)) {
|  vials.push(starName);
|  renderVials();
|  }
|  }
|

|  // Remove vial for star
|  function removeVial(starName) {
|  vials = vials.filter(v => v !== starName);
|  // Also remove from distribution if present
|  for (const tz in distributedVials) {
|  distributedVials[tz] = distributedVials[tz].filter(v => v !== starName);
|  if (distributedVials[tz].length === 0) delete distributedVials[tz];
|  }
|  renderVials();
|  renderDistributedVials();
|  updateTimezoneGrid();
|  }
|

|  // Render vials visually in vials container (draggable)
|  function renderVials() {
|  vialsContainer.innerHTML = "";
|  vials.forEach((starName) => {
|  const vial = document.createElement("div");
|  vial.className = "star-filled-vial";
|  vial.title = `Energy vial glowing green, representing collected energy from star ${starName}`;
|  vial.setAttribute("draggable", "true");
|  vial.setAttribute("aria-grabbed", "false");
|  vial.setAttribute("tabindex", "0");
|  vial.dataset.starName = starName;
|  vial.innerHTML = `
|  <img src="https://placehold.co/48x48/png?text=Vial" alt="Energy vial glowing green, representing collected energy from star ${starName}" class="w-full h-auto rounded-t" />
|  <div class="vial-liquid"></div>
|  <div class="text-xs text-green-300 text-center mt-1 select-none truncate" title="${starName}">${starName}</div>
|  `;
|  vialsContainer.appendChild(vial);
|  });
|  addDragAndDropListeners();
|  }
|

|  // Render distributed vials visually in distribution container
|  function renderDistributedVials() {
|  distributionContainer.innerHTML = "";
|  for (const tz in distributedVials) {
|  distributedVials[tz].forEach(starName => {
|  const vial = document.createElement("div");
|  vial.className = "star-filled-vial";
|  vial.title = `Distributed energy vial from star ${starName} to timezone ${tz}`;
|  vial.setAttribute("draggable", "true");
|  vial.setAttribute("aria-grabbed", "false");
|  vial.setAttribute("tabindex", "0");
|  vial.dataset.starName = starName;
|  vial.dataset.timezone = tz;
|  vial.innerHTML = `
|  <img src="https://placehold.co/48x48/png?text=Vial" alt="Distributed energy vial glowing green, representing collected energy from star ${starName} distributed to timezone ${tz}" class="w-full h-auto rounded-t" />
|  <div class="vial-liquid"></div>
|  <div class="text-xs text-green-300 text-center mt-1 select-none truncate" title="${starName}">${starName}</div>
|  <div class="text-[8px] text-green-400 text-center select-none truncate mt-0.5" title="${tz}">${tz}</div>
|  `;
|  distributionContainer.appendChild(vial);
|  });
|  }
|  addDragAndDropListeners();
|  }
|

|  // Create beams and star dots on sphere
|  function createBeamsAndStars() {
|  beamsContainer.innerHTML = "";
|  allStars.forEach((star, index) => {
|  // Create star dot
|  const starDot = document.createElement("div");
|  starDot.className = "star-dot";
|  starDot.style.left = `${star.x}%`;
|  starDot.style.top = `${star.y}%`;
|  starDot.setAttribute("data-star-index", index);
|  starDot.setAttribute("tabindex", "0");
|  starDot.setAttribute("role", "button");
|  starDot.setAttribute("aria-label", `Star ${star.name} in constellation ${star.constellation}, ${star.harnessed ? "harnessed" : "not harnessed"}`);
|  starDot.title = `${star.name} (${star.constellation}) - ${star.harnessed ? "Harnessed" : "To Harness"}`;
|  if (star.harnessed) {
|  starDot.style.backgroundColor = "#4ade80";
|  starDot.style.boxShadow = "0 0 12px #4ade80";
|  } else {
|  starDot.style.backgroundColor = "#eab308";
|  starDot.style.boxShadow = "0 0 10px #ca8a04";
|  }
|  // Add voice icon overlay if voice enabled
|  if (star.voice) {
|  const voiceIcon = document.createElement("i");
|  voiceIcon.className = "fas fa-microphone voice-icon";
|  voiceIcon.style.position = "absolute";
|  voiceIcon.style.top = "-6px";
|  voiceIcon.style.right = "-6px";
|  voiceIcon.style.fontSize = "0.75rem";
|  voiceIcon.style.color = "#22c55e";
|  starDot.appendChild(voiceIcon);
|  }
|  // Add brain icon overlay if brain insurance enabled
|  if (star.brain) {
|  const brainIcon = document.createElement("i");
|  brainIcon.className = "fas fa-brain brain-icon";
|  brainIcon.style.position = "absolute";
|  brainIcon.style.bottom = "-6px";
|  brainIcon.style.left = "-6px";
|  brainIcon.style.fontSize = "0.75rem";
|  brainIcon.style.color = "#22c55e";
|  starDot.appendChild(brainIcon);
|  }
|  beamsContainer.appendChild(starDot);
|

|  // Create beam line from sphere center to star dot
|  const beamLine = document.createElement("div");
|  beamLine.className = "beam-line";
|  // Calculate distance and angle from center (50%,50%) to star (x,y)
|  const centerX = 50;
|  const centerY = 50;
|  const dx = star.x - centerX;
|  const dy = star.y - centerY;
|  const distance = Math.sqrt(dx * dx + dy * dy);
|  const angle = Math.atan2(dy, dx) * (180 / Math.PI) + 90; // +90 to align vertical top
|  beamLine.style.height = `${distance * 1.4}%`; // scale length a bit longer
|  beamLine.style.left = "50%";
|  beamLine.style.top = "50%";
|  beamLine.style.transform = `translateX(-50%) rotate(${angle}deg)`;
|  beamsContainer.appendChild(beamLine);
|  });
|  }
|

|  // Update star dot appearance after changes
|  function updateStarDot(starName) {
|  const starIndex = allStars.findIndex(s => s.name === starName);
|  if (starIndex === -1) return;
|  const star = allStars[starIndex];
|  const starDot = beamsContainer.querySelector(`.star-dot[data-star-index="${starIndex}"]`);
|  if (!starDot) return;
|  // Update color and shadow
|  if (star.harnessed) {
|  starDot.style.backgroundColor = "#4ade80";
|  starDot.style.boxShadow = "0 0 12px #4ade80";
|  } else {
|  starDot.style.backgroundColor = "#eab308";
|  starDot.style.boxShadow = "0 0 10px #ca8a04";
|  }
|  // Remove existing voice and brain icons
|  starDot.querySelectorAll(".voice-icon, .brain-icon").forEach(el => el.remove());
|  // Add voice icon overlay if voice enabled
|  if (star.voice) {
|  const voiceIcon = document.createElement("i");
|  voiceIcon.className = "fas fa-microphone voice-icon";
|  voiceIcon.style.position = "absolute";
|  voiceIcon.style.top = "-6px";
|  voiceIcon.style.right = "-6px";
|  voiceIcon.style.fontSize = "0.75rem";
|  voiceIcon.style.color = "#22c55e";
|  starDot.appendChild(voiceIcon);
|  }
|  // Add brain icon overlay if brain insurance enabled
|  if (star.brain) {
|  const brainIcon = document.createElement("i");
|  brainIcon.className = "fas fa-brain brain-icon";
|  brainIcon.style.position = "absolute";
|  brainIcon.style.bottom = "-6px";
|  brainIcon.style.left = "-6px";
|  brainIcon.style.fontSize = "0.75rem";
|  brainIcon.style.color = "#22c55e";
|  starDot.appendChild(brainIcon);
|  }
|  starDot.title = `${star.name} (${star.constellation}) - ${star.harnessed ? "Harnessed" : "To Harness"}`;
|  starDot.setAttribute("aria-label", `Star ${star.name} in constellation ${star.constellation}, ${star.harnessed ? "harnessed" : "not harnessed"}`);
|  }
|

|  // Animate harnessing sequence
|  function startHarnessingSequence() {
|  if (harnessing) return;
|  harnessing = true;
|  btnStart.disabled = true;
|  btnStop.disabled = false;
|  terminalInput.disabled = false;
|  terminalInput.focus();
|

|  terminalPrint("Starting harnessing sequence...");
|  currentHarnessIndex = 0;
|

|  harnessInterval = setInterval(() => {
|  if (currentHarnessIndex >= allStars.length) {
|  terminalPrint("Harnessing sequence complete.");
|  stopHarnessingSequence();
|  return;
|  }
|  const star = allStars[currentHarnessIndex];
|  if (!star.harnessed) {
|  star.harnessed = true;
|  addVial(star.name);
|  updateStarLists();
|  updateStarDot(star.name);
|  terminalPrint(`Harnessed star: ${star.name} (${star.constellation})`);
|  animateBeamPulse(star);
|  } else {
|  terminalPrint(`Star already harnessed: ${star.name} (${star.constellation})`);
|  }
|  currentHarnessIndex++;
|  }, 2500);
|  }
|

|  function stopHarnessingSequence() {
|  if (!harnessing) return;
|  harnessing = false;
|  btnStart.disabled = false;
|  btnStop.disabled = true;
|  terminalInput.disabled = true;
|  clearInterval(harnessInterval);
|  terminalPrint("Harnessing sequence stopped. Consumption continues.");
|  }
|

|  // Terminal print helper
|  function terminalPrint(text) {
|  const p = document.createElement("div");
|  p.textContent = text;
|  terminalOutput.appendChild(p);
|  terminal.scrollTop = terminal.scrollHeight;
|  }
|

|  // Terminal command handler
|  function handleTerminalCommand(input) {
|  if (!input.trim()) return;
|  const parts = input.trim().split(/\s+/);
|  const cmd = parts[0].toLowerCase();
|  const args = parts.slice(1);
|

|  if (!(cmd in commands)) {
|  terminalPrint(`Error: Command '${cmd}' not recognized. Type 'help' for commands.`);
|  return;
|  }
|

|  // Restrict some commands to Antonio Rodriguez Jr.
|  const restrictedCommands = ["harness", "unharness", "brain"];
|  if (restrictedCommands.includes(cmd) && currentUser !== "Antonio Rodriguez Jr.") {
|  terminalPrint(`Access denied: Only Antonio Rodriguez Jr. can execute '${cmd}'.`);
|  return;
|  }
|

|  const result = commands[cmd].action(args);
|  if (result) terminalPrint(result);
|  }
|

|  // Terminal input event
|  terminalInput.addEventListener("keydown", (e) => {
|  if (e.key === "Enter") {
|  e.preventDefault();
|  const input = terminalInput.value;
|  terminalPrint(`> ${input}`);
|  handleTerminalCommand(input);
|  terminalInput.value = "";
|  }
|  });
|

|  // Start/Stop buttons events
|  btnStart.addEventListener("click", () => {
|  startHarnessingSequence();
|  });
|  btnStop.addEventListener("click", () => {
|  stopHarnessingSequence();
|  });
|

|  // Animate beam pulse for a star
|  function animateBeamPulse(star) {
|  const starIndex = allStars.findIndex(s => s.name === star.name);
|  if (starIndex === -1) return;
|  // Find the beam line corresponding to star (beam lines are after star dots, so index*2+1)
|  const beamLines = beamsContainer.querySelectorAll(".beam-line");
|  const beamLine = beamLines[starIndex];
|  if (!beamLine) return;
|  beamLine.style.animation = "beam-glow-pulse 1.5s ease-in-out 3";
|  beamLine.addEventListener("animationend", () => {
|  beamLine.style.animation = "beam-glow 2s ease-in-out infinite alternate";
|  }, { once: true });
|  }
|

|  // Add keyboard and mouse interaction for star dots
|  function addStarDotInteractions() {
|  beamsContainer.querySelectorAll(".star-dot").forEach(starDot => {
|  starDot.addEventListener("mouseenter", (e) => {
|  const index = parseInt(starDot.getAttribute("data-star-index"));
|  showTooltip(e, allStars[index]);
|  });
|  starDot.addEventListener("mouseleave", () => {
|  hideTooltip();
|  });
|  starDot.addEventListener("focus", (e) => {
|  const index = parseInt(starDot.getAttribute("data-star-index"));
|  showTooltip(e, allStars[index]);
|  });
|  starDot.addEventListener("blur", () => {
|  hideTooltip();
|  });
|  starDot.addEventListener("click", () => {
|  const index = parseInt(starDot.getAttribute("data-star-index"));
|  const star = allStars[index];
|  terminalPrint(`> harness ${star.name}`);
|  if (star.harnessed) {
|  terminalPrint(`Star '${star.name}' is already harnessed.`);
|  } else {
|  star.harnessed = true;
|  addVial(star.name);
|  updateStarLists();
|  updateStarDot(star.name);
|  terminalPrint(`Star '${star.name}' is now harnessed and energy vial collected.`);
|  animateBeamPulse(star);
|  }
|  });
|  starDot.addEventListener("keydown", (e) => {
|  if (e.key === "Enter" || e.key === " ") {
|  e.preventDefault();
|  starDot.click();
|  }
|  });
|  });
|  }
|

|  // Tooltip show/hide
|  function showTooltip(event, star) {
|  tooltip.textContent = `${star.name} (${star.constellation}) - ${star.harnessed ? "Harnessed" : "To Harness"}`;
|  tooltip.style.left = `${event.target.offsetLeft + 20}px`;
|  tooltip.style.top = `${event.target.offsetTop - 30}px`;
|  tooltip.classList.add("visible");
|  tooltip.setAttribute("aria-hidden", "false");
|  }
|  function hideTooltip() {
|  tooltip.classList.remove("visible");
|  tooltip.setAttribute("aria-hidden", "true");
|  }
|

|  // Drag & Drop handlers for vials and distribution
|

|  function addDragAndDropListeners() {
|  // Draggables
|  const draggables = document.querySelectorAll(".star-filled-vial[draggable='true']");
|  draggables.forEach(draggable => {
|  draggable.removeEventListener("dragstart", onDragStart);
|  draggable.removeEventListener("dragend", onDragEnd);
|  draggable.addEventListener("dragstart", onDragStart);
|  draggable.addEventListener("dragend", onDragEnd);
|  draggable.removeEventListener("keydown", onDraggableKeyDown);
|  draggable.addEventListener("keydown", onDraggableKeyDown);
|  });
|

|  // Drop zones
|  [vialsContainer, distributionContainer].forEach(zone => {
|  zone.removeEventListener("dragover", onDragOver);
|  zone.removeEventListener("drop", onDrop);
|  zone.removeEventListener("dragleave", onDragLeave);
|  zone.addEventListener("dragover", onDragOver);
|  zone.addEventListener("drop", onDrop);
|  zone.addEventListener("dragleave", onDragLeave);
|  });
|  }
|

|  let draggedVial = null;
|

|  function onDragStart(e) {
|  draggedVial = e.target;
|  e.dataTransfer.effectAllowed = "move";
|  e.dataTransfer.setData("text/plain", draggedVial.dataset.starName);
|  draggedVial.setAttribute("aria-grabbed", "true");
|  setTimeout(() => {
|  draggedVial.style.visibility = "hidden";
|  }, 0);
|  }
|

|  function onDragEnd(e) {
|  if (draggedVial) {
|  draggedVial.style.visibility = "visible";
|  draggedVial.setAttribute("aria-grabbed", "false");
|  draggedVial = null;
|  }
|  [vialsContainer, distributionContainer].forEach(zone => {
|  zone.classList.remove("dragover");
|  });
|  }
|

|  function onDragOver(e) {
|  e.preventDefault();
|  e.dataTransfer.dropEffect = "move";
|  e.currentTarget.classList.add("dragover");
|  }
|

|  function onDragLeave(e) {
|  e.currentTarget.classList.remove("dragover");
|  }
|

|  function onDrop(e) {
|  e.preventDefault();
|  e.currentTarget.classList.remove("dragover");
|  const starName = e.dataTransfer.getData("text/plain");
|  if (!starName) return;
|

|  // Determine source and target containers
|  const sourceIsVials = vials.includes(starName);
|  const targetIsVials = e.currentTarget === vialsContainer;
|  const targetIsDistribution = e.currentTarget === distributionContainer;
|

|  if (sourceIsVials && targetIsDistribution) {
|  // Move vial from vials to distribution - assign to a timezone
|  // Prompt user to select timezone
|  promptTimezoneSelection(starName);
|  } else if (!sourceIsVials && targetIsVials) {
|  // Move vial back from distribution to vials (remove from distribution)
|  removeVialFromDistribution(starName);
|  }
|  }
|

|  // Prompt user to select timezone for vial distribution
|  function promptTimezoneSelection(starName) {
|  // Create modal-like prompt with timezone grid and confirm button
|  const modal = document.createElement("div");
|  modal.setAttribute("role", "dialog");
|  modal.setAttribute("aria-modal", "true");
|  modal.setAttribute("aria-label", `Select timezone to distribute energy vial from star ${starName}`);
|  modal.style.position = "fixed";
|  modal.style.top = "0";
|  modal.style.left = "0";
|  modal.style.width = "100vw";
|  modal.style.height = "100vh";
|  modal.style.backgroundColor = "rgba(0,0,0,0.85)";
|  modal.style.display = "flex";
|  modal.style.flexDirection = "column";
|  modal.style.justifyContent = "center";
|  modal.style.alignItems = "center";
|  modal.style.zIndex = "9999";
|  modal.style.padding = "1rem";
|

|  const container = document.createElement("div");
|  container.style.backgroundColor = "#111827";
|  container.style.border = "2px solid #22c55e";
|  container.style.borderRadius = "0.75rem";
|  container.style.padding = "1rem";
|  container.style.maxWidth = "600px";
|  container.style.width = "100%";
|  container.style.maxHeight = "80vh";
|  container.style.overflowY = "auto";
|  container.style.display = "flex";
|  container.style.flexDirection = "column";
|  container.style.gap = "1rem";
|

|  const title = document.createElement("h2");
|  title.textContent = `Select Timezone for Vial: ${starName}`;
|  title.style.color = "#22c55e";
|  title.style.fontFamily = "'Orbitron', monospace";
|  title.style.marginBottom = "0.5rem";
|  container.appendChild(title);
|

|  const tzGrid = document.createElement("div");
|  tzGrid.style.display = "grid";
|  tzGrid.style.gridTemplateColumns = "repeat(auto-fill,minmax(120px,1fr))";
|  tzGrid.style.gap = "0.5rem";
|  tzGrid.style.maxHeight = "50vh";
|  tzGrid.style.overflowY = "auto";
|

|  let selectedTz = null;
|

|  timezones.forEach(tz => {
|  const block = document.createElement("button");
|  block.type = "button";
|  block.className = "timezone-block";
|  block.textContent = `${tz.name} (${tz.offset})`;
|  block.style.userSelect = "none";
|  block.style.border = "1px solid #22c55e";
|  block.style.backgroundColor = "#064e3b";
|  block.style.color = "#a7f3d0";
|  block.style.borderRadius = "0.5rem";
|  block.style.padding = "0.5rem";
|  block.style.fontSize = "0.75rem";
|  block.style.cursor = "pointer";
|  block.setAttribute("aria-pressed", "false");
|  block.addEventListener("click", () => {
|  // Deselect all
|  Array.from(tzGrid.children).forEach(c => {
|  c.classList.remove("active");
|  c.setAttribute("aria-pressed", "false");
|  });
|  block.classList.add("active");
|  block.setAttribute("aria-pressed", "true");
|  selectedTz = tz.id;
|  confirmBtn.disabled = false;
|  confirmBtn.focus();
|  });
|  tzGrid.appendChild(block);
|  });
|

|  container.appendChild(tzGrid);
|

|  const btnContainer = document.createElement("div");
|  btnContainer.style.display = "flex";
|  btnContainer.style.justifyContent = "flex-end";
|  btnContainer.style.gap = "1rem";
|

|  const cancelBtn = document.createElement("button");
|  cancelBtn.type = "button";
|  cancelBtn.textContent = "Cancel";
|  cancelBtn.className = "btn-red px-3 py-1 rounded";
|  cancelBtn.addEventListener("click", () => {
|  document.body.removeChild(modal);
|  });
|

|  const confirmBtn = document.createElement("button");
|  confirmBtn.type = "button";
|  confirmBtn.textContent = "Confirm";
|  confirmBtn.className = "btn-green px-3 py-1 rounded";
|  confirmBtn.disabled = true;
|  confirmBtn.addEventListener("click", () => {
|  if (!selectedTz) return;
|  distributeVialToTimezone(starName, selectedTz);
|  document.body.removeChild(modal);
|  });
|

|  btnContainer.appendChild(cancelBtn);
|  btnContainer.appendChild(confirmBtn);
|  container.appendChild(btnContainer);
|

|  modal.appendChild(container);
|  document.body.appendChild(modal);
|

|  // Focus first timezone block for accessibility
|  const firstTzBtn = tzGrid.querySelector("button");
|  if (firstTzBtn) firstTzBtn.focus();
|  }
|

|  // Distribute vial to timezone
|  function distributeVialToTimezone(starName, timezoneId) {
|  // Remove vial from vials container
|  vials = vials.filter(v => v !== starName);
|  // Add vial to distribution mapping
|  if (!distributedVials[timezoneId]) {
|  distributedVials[timezoneId] = [];
|  }
|  if (!distributedVials[timezoneId].includes(starName)) {
|  distributedVials[timezoneId].push(starName);
|  }
|  renderVials();
|  renderDistributedVials();
|  updateTimezoneGrid();
|  terminalPrint(`Distributed vial from star '${starName}' to timezone '${timezoneId}'.`);
|  }
|

|  // Remove vial from distribution (back to vials container)
|  function removeVialFromDistribution(starName) {
|  let found = false;
|  for (const tz in distributedVials) {
|  const index = distributedVials[tz].indexOf(starName);
|  if (index !== -1) {
|  distributedVials[tz].splice(index, 1);
|  if (distributedVials[tz].length === 0) delete distributedVials[tz];
|  found = true;
|  break;
|  }
|  }
|  if (found) {
|  vials.push(starName);
|  renderVials();
|  renderDistributedVials();
|  updateTimezoneGrid();
|  terminalPrint(`Removed vial from distribution for star '${starName}'.`);
|  }
|  }
|

|  // Update timezone grid to show which timezones have energy distributed
|  function updateTimezoneGrid() {
|  timezoneGrid.innerHTML = "";
|  timezones.forEach(tz => {
|  const block = document.createElement("div");
|  block.className = "timezone-block";
|  block.textContent = `${tz.name} (${tz.offset})`;
|  if (distributedVials[tz.id] && distributedVials[tz.id].length > 0) {
|  block.classList.add("active");
|  block.title = `Energy vials distributed: ${distributedVials[tz.id].join(", ")}`;
|  } else {
|  block.title = "No energy distributed";
|  }
|  timezoneGrid.appendChild(block);
|  });
|  }
|

|  // Drag & Drop keyboard support for vials
|  function onDraggableKeyDown(e) {
|  if (e.key === "Enter" || e.key === " ") {
|  e.preventDefault();
|  const vial = e.currentTarget;
|  if (vial.parentElement === vialsContainer) {
|  // Move vial to distribution - prompt timezone selection
|  promptTimezoneSelection(vial.dataset.starName);
|  } else if (vial.parentElement === distributionContainer) {
|  // Move vial back to vials container
|  removeVialFromDistribution(vial.dataset.starName);
|  }
|  }
|  }
|

|  // Initial render
|  updateStarLists();
|  renderVials();
|  renderDistributedVials();
|  createBeamsAndStars();
|  addStarDotInteractions();
|  updateTimezoneGrid();
|

|  // Initial terminal welcome message
|  terminalPrint("Welcome to the Star Communication Terminal.");
|  terminalPrint("Type 'help' to see available commands.");
|

|  // Accessibility: focus terminal input on load
|  window.addEventListener("load", () => {
|  terminalInput.disabled = true;
|  });
|  </script>
|  </body>
| </html>

<html class="scroll-smooth" lang="en">
|  <head>
|  <meta charset="utf-8"/>
|  <meta content="width=device-width, initial-scale=1" name="viewport"/>
|  <title>
|  Smart Sphere Star Harnessing App
|  </title>
|  <script src="https://cdn.tailwindcss.com">
|  </script>
|  <link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/5.15.3/css/all.min.css" rel="stylesheet"/>
|  <link href="https://fonts.googleapis.com/css2?family=Orbitron&amp;family=Roboto+Mono&amp;display=swap" rel="stylesheet"/>
|  <style>
|  body {
|  font-family: 'Roboto Mono', monospace;
|  background-color: #0f172a;
|  color: #d1d5db;
|  }
|  .terminal {
|  background-color: #111827;
|  border-radius: 0.5rem;
|  box-shadow: 0 0 15px #22c55e;
|  font-family: 'Roboto Mono', monospace;
|  font-size: 0.875rem;
|  line-height: 1.25rem;
|  color: #22c55e;
|  padding: 1rem;
|  min-height: 300px;
|  overflow-y: auto;
|  white-space: pre-wrap;
|  user-select: text;
|  }
|  .terminal-input {
|  outline: none;
|  border: none;
|  background: transparent;
|  color: #22c55e;
|  font-family: 'Roboto Mono', monospace;
|  font-size: 0.875rem;
|  width: 100%;
|  caret-color: #22c55e;
|  }
|  .scrollbar-thin::-webkit-scrollbar {
|  width: 6px;
|  }
|  .scrollbar-thin::-webkit-scrollbar-track {
|  background: transparent;
|  }
|  .scrollbar-thin::-webkit-scrollbar-thumb {
|  background-color: #22c55e;
|  border-radius: 3px;
|  }
|  .star-filled-vial {
|  width: 48px;
|  height: 96px;
|  background: linear-gradient(180deg, #22c55e 0%, #166534 100%);
|  border-radius: 0.75rem 0.75rem 0.25rem 0.25rem;
|  box-shadow: 0 0 8px #22c55e;
|  position: relative;
|  margin: 0.25rem;
|  display: flex;
|  flex-direction: column;
|  justify-content: flex-end;
|  overflow: hidden;
|  cursor: grab;
|  transition: transform 0.3s ease;
|  }
|  .star-filled-vial:active {
|  cursor: grabbing;
|  transform: scale(1.1);
|  box-shadow: 0 0 20px #4ade80;
|  z-index: 1000;
|  }
|  .star-filled-vial:hover {
|  transform: scale(1.1);
|  box-shadow: 0 0 15px #4ade80;
|  z-index: 10;
|  }
|  .star-filled-vial::before {
|  content: '';
|  position: absolute;
|  top: 0.25rem;
|  left: 50%;
|  transform: translateX(-50%);
|  width: 24px;
|  height: 12px;
|  background: #166534;
|  border-radius: 12px 12px 0 0;
|  box-shadow: inset 0 2px 4px #22c55e;
|  z-index: 10;
|  }
|  .vial-liquid {
|  background: #22c55e;
|  height: 60%;
|  border-radius: 0 0 0.75rem 0.75rem;
|  box-shadow: inset 0 0 10px #4ade80;
|  transition: height 0.5s ease;
|  }
|  .btn-green {
|  background-color: #22c55e;
|  color: #0f172a;
|  font-weight: 600;
|  transition: background-color 0.3s ease;
|  }
|  .btn-green:hover:not(:disabled) {
|  background-color: #16a34a;
|  }
|  .btn-green:disabled {
|  background-color: #4ade80;
|  cursor: not-allowed;
|  }
|  .btn-red {
|  background-color: #dc2626;
|  color: #fef2f2;
|  font-weight: 600;
|  transition: background-color 0.3s ease;
|  }
|  .btn-red:hover:not(:disabled) {
|  background-color: #b91c1c;
|  }
|  .btn-red:disabled {
|  background-color: #fca5a5;
|  cursor: not-allowed;
|  }
|  .btn-yellow {
|  background-color: #eab308;
|  color: #1e293b;
|  font-weight: 600;
|  transition: background-color 0.3s ease;
|  }
|  .btn-yellow:hover {
|  background-color: #ca8a04;
|  }
|  .scrollbar-thin {
|  scrollbar-width: thin;
|  scrollbar-color: #22c55e transparent;
|  }
|  /* Sphere container and beams animation */
|  .sphere-container {
|  position: relative;
|  width: 100%;
|  max-width: 400px;
|  aspect-ratio: 1 / 1;
|  margin: 0 auto;
|  perspective: 1200px;
|  }
|  .sphere {
|  width: 100%;
|  height: 100%;
|  border-radius: 50%;
|  background: radial-gradient(circle at center, #22c55e 20%, #064e3b 90%);
|  box-shadow:
|  inset 0 0 20px #4ade80,
|  0 0 30px #22c55e;
|  position: relative;
|  transform-style: preserve-3d;
|  animation: sphere-rotate 20s linear infinite;
|  }
|  @keyframes sphere-rotate {
|  0% {
|  transform: rotateX(0deg) rotateY(0deg);
|  }
|  100% {
|  transform: rotateX(360deg) rotateY(360deg);
|  }
|  }
|  /* Beams container */
|  .beams-container {
|  position: absolute;
|  top: 50%;
|  left: 50%;
|  width: 100%;
|  height: 100%;
|  pointer-events: none;
|  transform-style: preserve-3d;
|  transform-origin: center center;
|  animation: beams-pulse 3s ease-in-out infinite;
|  }
|  @keyframes beams-pulse {
|  0%, 100% {
|  filter: drop-shadow(0 0 6px #22c55e);
|  }
|  50% {
|  filter: drop-shadow(0 0 12px #4ade80);
|  }
|  }
|  /* Beam line */
|  .beam-line {
|  position: absolute;
|  width: 2px;
|  background: linear-gradient(180deg, #22c55e, transparent);
|  border-radius: 1px;
|  transform-origin: top center;
|  animation: beam-glow 2s ease-in-out infinite alternate;
|  filter: drop-shadow(0 0 4px #22c55e);
|  }
|  @keyframes beam-glow {
|  0% {
|  opacity: 0.6;
|  box-shadow: 0 0 6px #22c55e;
|  }
|  100% {
|  opacity: 1;
|  box-shadow: 0 0 14px #4ade80;
|  }
|  }
|  /* Star dot */
|  .star-dot {
|  position: absolute;
|  width: 12px;
|  height: 12px;
|  background: #22c55e;
|  border-radius: 50%;
|  box-shadow: 0 0 8px #4ade80;
|  cursor: pointer;
|  transition: transform 0.3s ease;
|  }
|  .star-dot:hover {
|  transform: scale(1.5);
|  box-shadow: 0 0 20px #86efac;
|  z-index: 20;
|  }
|  /* Voice & Brain info box */
|  .info-box {
|  background: #064e3b;
|  border: 2px solid #22c55e;
|  border-radius: 0.5rem;
|  padding: 1rem;
|  margin-top: 1rem;
|  color: #a7f3d0;
|  font-size: 0.9rem;
|  font-family: 'Roboto Mono', monospace;
|  user-select: none;
|  }
|  /* Voice icon animation */
|  .voice-icon {
|  animation: pulse-voice 2s infinite;
|  color: #22c55e;
|  font-size: 1.5rem;
|  vertical-align: middle;
|  margin-right: 0.5rem;
|  }
|  @keyframes pulse-voice {
|  0%, 100% {
|  opacity: 1;
|  text-shadow: 0 0 6px #22c55e;
|  }
|  50% {
|  opacity: 0.6;
|  text-shadow: 0 0 12px #4ade80;
|  }
|  }
|  /* Brain icon animation */
|  .brain-icon {
|  animation: pulse-brain 3s infinite;
|  color: #22c55e;
|  font-size: 1.5rem;
|  vertical-align: middle;
|  margin-right: 0.5rem;
|  }
|  @keyframes pulse-brain {
|  0%, 100% {
|  opacity: 1;
|  text-shadow: 0 0 6px #22c55e;
|  }
|  50% {
|  opacity: 0.7;
|  text-shadow: 0 0 14px #4ade80;
|  }
|  }
|  /* Scrollable star list with custom scrollbar */
|  .star-list {
|  max-height: 180px;
|  overflow-y: auto;
|  scrollbar-width: thin;
|  scrollbar-color: #22c55e transparent;
|  }
|  .star-list::-webkit-scrollbar {
|  width: 6px;
|  }
|  .star-list::-webkit-scrollbar-track {
|  background: transparent;
|  }
|  .star-list::-webkit-scrollbar-thumb {
|  background-color: #22c55e;
|  border-radius: 3px;
|  }
|  /* Tooltip for star dots */
|  .tooltip {
|  position: absolute;
|  background: #064e3b;
|  border: 1px solid #22c55e;
|  padding: 0.25rem 0.5rem;
|  border-radius: 0.25rem;
|  font-size: 0.75rem;
|  color: #a7f3d0;
|  pointer-events: none;
|  white-space: nowrap;
|  user-select: none;
|  z-index: 50;
|  opacity: 0;
|  transition: opacity 0.2s ease;
|  }
|  .tooltip.visible {
|  opacity: 1;
|  }
|  /* Drag & Drop container styles */
|  #vials-container, #distribution-container {
|  min-height: 120px;
|  border: 2px dashed #22c55e;
|  border-radius: 0.5rem;
|  padding: 0.5rem;
|  display: flex;
|  flex-wrap: wrap;
|  gap: 0.5rem;
|  background-color: #0f172a;
|  transition: background-color 0.3s ease;
|  }
|  #vials-container.dragover, #distribution-container.dragover {
|  background-color: #164e2e;
|  border-color: #4ade80;
|  }
|  /* Distribution section */
|  #distribution-section {
|  background-color: #111827;
|  border-radius: 0.75rem;
|  padding: 1rem;
|  margin-top: 1rem;
|  color: #a7f3d0;
|  font-family: 'Roboto Mono', monospace;
|  }
|  #distribution-section h3 {
|  font-family: 'Orbitron', monospace;
|  color: #22c55e;
|  margin-bottom: 0.5rem;
|  }
|  /* Timezone grid */
|  #timezone-grid {
|  display: grid;
|  grid-template-columns: repeat(auto-fill,minmax(120px,1fr));
|  gap: 0.5rem;
|  max-height: 300px;
|  overflow-y: auto;
|  border: 1px solid #22c55e;
|  border-radius: 0.5rem;
|  padding: 0.5rem;
|  background-color: #0f172a;
|  }
|  .timezone-block {
|  background-color: #064e3b;
|  border: 1px solid #22c55e;
|  border-radius: 0.5rem;
|  padding: 0.5rem;
|  font-size: 0.75rem;
|  text-align: center;
|  user-select: none;
|  cursor: default;
|  color: #a7f3d0;
|  display: flex;
|  flex-direction: column;
|  justify-content: center;
|  align-items: center;
|  min-height: 60px;
|  transition: background-color 0.3s ease;
|  }
|  .timezone-block.active {
|  background-color: #22c55e;
|  color: #0f172a;
|  font-weight: 700;
|  box-shadow: 0 0 10px #4ade80;
|  }
|  /* Responsive tweaks */
|  @media (max-width: 768px) {
|  main {
|  grid-template-columns: 1fr !important;
|  }
|  #distribution-section {
|  margin-top: 1.5rem;
|  }
|  }
|  </style>
|  </head>
|  <body class="min-h-screen flex flex-col">
|  <header class="bg-gray-900 p-4 flex flex-col md:flex-row items-center justify-between">
|  <div class="flex items-center space-x-3">
|  <img alt="Smart tracking sphere, metallic silver with green glowing lines, floating in space" class="w-12 h-12 rounded-full" src="https://placehold.co/48x48/png?text=Sphere"/>
|  <h1 class="text-2xl font-orbitron font-bold text-green-400 select-none">
|  Smart Sphere Star Harnessing
|  </h1>
|  </div>
|  <nav class="mt-3 md:mt-0">
|  <ul class="flex space-x-6 text-green-300 font-semibold text-sm select-none">
|  <li>
|  <button aria-label="Start harnessing process" class="btn-green px-3 py-1 rounded flex items-center space-x-2" id="btn-start">
|  <i aria-hidden="true" class="fas fa-play">
|  </i>
|  <span>
|  Start Harness
|  </span>
|  </button>
|  </li>
|  <li>
|  <button aria-label="Stop harnessing process" class="btn-red px-3 py-1 rounded flex items-center space-x-2" disabled="" id="btn-stop">
|  <i aria-hidden="true" class="fas fa-stop">
|  </i>
|  <span>
|  Stop Harness
|  </span>
|  </button>
|  </li>
|  </ul>
|  </nav>
|  </header>
|  <main class="flex-grow p-4 max-w-7xl mx-auto grid grid-cols-1 md:grid-cols-4 gap-6">
|  <!-- Sphere & Beams Section -->
|  <section class="col-span-1 md:col-span-2 bg-gray-800 rounded-lg p-4 flex flex-col items-center relative">
|  <div aria-label="Smart sphere with tracking beams" class="sphere-container">
|  <div class="sphere" id="sphere">
|  </div>
|  <div aria-hidden="true" class="beams-container" id="beams-container">
|  </div>
|  <div aria-hidden="true" class="tooltip" id="tooltip" role="tooltip">
|  </div>
|  </div>
|  <p class="mt-4 text-green-300 text-center font-mono text-sm max-w-xl">
|  The sphere intelligently tracks stars and harnesses their energy by searching constellations and individual stars. Click on stars to see details.
|  </p>
|  <div aria-atomic="true" aria-live="polite" class="info-box mt-6 w-full max-w-xl" id="voice-brain-info">
|  <div class="flex items-center mb-2">
|  <i aria-hidden="true" class="fas fa-microphone voice-icon">
|  </i>
|  <span>
|  <strong>
|  Voice Enabled:
|  </strong>
|  The sphere can communicate with stars using voice commands.
|  </span>
|  </div>
|  <div class="flex items-center">
|  <i aria-hidden="true" class="fas fa-brain brain-icon">
|  </i>
|  <span>
|  <strong>
|  Brain Insurance:
|  </strong>
|  Only
|  <em>
|  Antonio Rodriguez Jr.
|  </em>
|  can convert, channel, stream, listen, touch, smell, feel, and manage star energy.
|  </span>
|  </div>
|  </div>
|  </section>
|  <!-- Star List & Vials Section -->
|  <section class="col-span-1 md:col-span-2 bg-gray-900 rounded-lg p-4 flex flex-col">
|  <h2 class="text-green-400 font-orbitron text-xl mb-3 select-none">
|  Stars Harnessed &amp; To Harness
|  </h2>
|  <div class="flex flex-col space-y-4 overflow-y-auto max-h-[400px] scrollbar-thin pr-2">
|  <div>
|  <h3 class="text-green-300 font-semibold mb-1">
|  Harnessed Stars
|  </h3>
|  <ul aria-label="List of harnessed stars" class="list-disc list-inside text-green-200 star-list" id="list-harnessed" tabindex="0">
|  </ul>
|  </div>
|  <div>
|  <h3 class="text-yellow-400 font-semibold mb-1">
|  Stars To Harness
|  </h3>
|  <ul aria-label="List of stars to harness" class="list-disc list-inside text-yellow-300 star-list" id="list-to-harness" tabindex="0">
|  </ul>
|  </div>
|  </div>
|  <h2 class="text-green-400 font-orbitron text-xl mt-6 mb-3 select-none">
|  Collected Vials (Drag to Distribute Energy)
|  </h2>
|  <div aria-dropeffect="move" aria-label="Collected energy vials" class="flex flex-wrap gap-2 min-h-[120px]" id="vials-container" tabindex="0">
|  </div>
|  <section aria-label="Energy distribution section" id="distribution-section" tabindex="0">
|  <h3>
|  Energy Distribution Across Timezones
|  </h3>
|  <p class="mb-2 text-sm text-green-300">
|  Drag vials here to distribute star energy to real-life locations worldwide using IP blocks and timezone coverage. All timezones are included to ensure universal interest reception.
|  </p>
|  <div aria-dropeffect="move" aria-label="Distributed energy vials container" class="min-h-[120px] flex flex-wrap gap-2" id="distribution-container" tabindex="0">
|  </div>
|  <h3 class="mt-4">
|  Timezones
|  </h3>
|  <div aria-label="List of all world timezones with energy distribution status" id="timezone-grid" tabindex="0">
|  </div>
|  </section>
|  </section>
|  </main>
|  <!-- Terminal Section -->
|  <section class="bg-gray-900 p-4 max-w-7xl mx-auto rounded-lg mt-6 mb-6">
|  <h2 class="text-green-400 font-orbitron text-xl mb-3 select-none">
|  Star Communication Terminal
|  </h2>
|  <div aria-atomic="true" aria-label="Star communication terminal" aria-live="polite" aria-multiline="true" class="terminal scrollbar-thin" contenteditable="false" id="terminal" role="textbox" tabindex="0">
|  <div aria-atomic="true" aria-live="polite" class="mb-2" id="terminal-output">
|  </div>
|  <div class="flex items-center space-x-2">
|  <span aria-hidden="true" class="text-green-400 font-bold select-none">
|  &gt;
|  </span>
|  <input aria-label="Terminal command input" autocomplete="off" class="terminal-input flex-grow" disabled="" id="terminal-input" spellcheck="false" type="text"/>
|  </div>
|  </div>
|  </section>
|  <script>
|  // Data for stars with 3D positions (x,y in % relative to sphere container)
|  const allStars = [
|  { name: "Sirius", constellation: "Canis Major", harnessed: true, x: 70, y: 30, voice: true, brain: true },
|  { name: "Betelgeuse", constellation: "Orion", harnessed: true, x: 40, y: 20, voice: true, brain: false },
|  { name: "Rigel", constellation: "Orion", harnessed: false, x: 45, y: 60, voice: false, brain: false },
|  { name: "Vega", constellation: "Lyra", harnessed: false, x: 80, y: 50, voice: false, brain: false },
|  { name: "Polaris", constellation: "Ursa Minor", harnessed: true, x: 50, y: 10, voice: true, brain: true },
|  { name: "Altair", constellation: "Aquila", harnessed: false, x: 60, y: 70, voice: false, brain: false },
|  { name: "Aldebaran", constellation: "Taurus", harnessed: false, x: 30, y: 40, voice: false, brain: false },
|  { name: "Antares", constellation: "Scorpius", harnessed: false, x: 20, y: 65, voice: false, brain: false },
|  { name: "Spica", constellation: "Virgo", harnessed: true, x: 35, y: 25, voice: true, brain: false },
|  { name: "Deneb", constellation: "Cygnus", harnessed: false, x: 75, y: 75, voice: false, brain: false },
|  { name: "Castor", constellation: "Gemini", harnessed: false, x: 55, y: 35, voice: false, brain: false },
|  { name: "Pollux", constellation: "Gemini", harnessed: false, x: 58, y: 38, voice: false, brain: false },
|  { name: "Procyon", constellation: "Canis Minor", harnessed: true, x: 65, y: 45, voice: true, brain: false },
|  { name: "Fomalhaut", constellation: "Piscis Austrinus", harnessed: false, x: 25, y: 55, voice: false, brain: false },
|  { name: "Regulus", constellation: "Leo", harnessed: false, x: 40, y: 75, voice: false, brain: false }
|  ];


|  // List of all timezones (IANA) with display names and UTC offsets
|  // For brevity, a representative subset of all timezones is included here.
|  // In a real app, you would include all timezones.
|  const timezones = [
|  { id: "Pacific/Midway", name: "Midway Island", offset: "-11:00" },
|  { id: "Pacific/Honolulu", name: "Hawaii", offset: "-10:00" },
|  { id: "America/Anchorage", name: "Alaska", offset: "-09:00" },
|  { id: "America/Los_Angeles", name: "Pacific Time (US & Canada)", offset: "-08:00" },
|  { id: "America/Denver", name: "Mountain Time (US & Canada)", offset: "-07:00" },
|  { id: "America/Chicago", name: "Central Time (US & Canada)", offset: "-06:00" },
|  { id: "America/New_York", name: "Eastern Time (US & Canada)", offset: "-05:00" },
|  { id: "America/Caracas", name: "Caracas", offset: "-04:30" },
|  { id: "America/Halifax", name: "Atlantic Time (Canada)", offset: "-04:00" },
|  { id: "America/St_Johns", name: "Newfoundland", offset: "-03:30" },
|  { id: "America/Argentina/Buenos_Aires", name: "Buenos Aires", offset: "-03:00" },
|  { id: "Atlantic/South_Georgia", name: "South Georgia", offset: "-02:00" },
|  { id: "Atlantic/Azores", name: "Azores", offset: "-01:00" },
|  { id: "Europe/London", name: "London", offset: "+00:00" },
|  { id: "Europe/Berlin", name: "Berlin", offset: "+01:00" },
|  { id: "Europe/Athens", name: "Athens", offset: "+02:00" },
|  { id: "Europe/Moscow", name: "Moscow", offset: "+03:00" },
|  { id: "Asia/Dubai", name: "Dubai", offset: "+04:00" },
|  { id: "Asia/Karachi", name: "Karachi", offset: "+05:00" },
|  { id: "Asia/Kolkata", name: "India Standard Time", offset: "+05:30" },
|  { id: "Asia/Bangkok", name: "Bangkok", offset: "+07:00" },
|  { id: "Asia/Shanghai", name: "Shanghai", offset: "+08:00" },
|  { id: "Asia/Tokyo", name: "Tokyo", offset: "+09:00" },
|  { id: "Australia/Sydney", name: "Sydney", offset: "+10:00" },
|  { id: "Pacific/Auckland", name: "Auckland", offset: "+12:00" },
|  { id: "Pacific/Chatham", name: "Chatham Islands", offset: "+12:45" }
|  ];


|  // Commands for terminal
|  const commands = {
|  help: {
|  description: "List available commands",
|  action: () => {
|  return Object.entries(commands)
|  .map(([cmd, obj]) => `${cmd} - ${obj.description}`)
|  .join("\n");
|  },
|  },
|  list: {
|  description: "List stars and their harness status",
|  action: () => {
|  let output = "Harnessed Stars:\n";
|  output += allStars.filter(s => s.harnessed).map(s => `- ${s.name} (${s.constellation})`).join("\n") + "\n\n";
|  output += "Stars To Harness:\n";
|  output += allStars.filter(s => !s.harnessed).map(s => `- ${s.name} (${s.constellation})`).join("\n");
|  return output;
|  },
|  },
|  harness: {
|  description: "Start harnessing a star by name. Usage: harness [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  if (star.harnessed) return `Star '${star.name}' is already harnessed.`;
|  star.harnessed = true;
|  updateStarLists();
|  addVial(star.name);
|  updateStarDot(star.name);
|  return `Star '${star.name}' is now harnessed and energy vial collected.`;
|  },
|  },
|  unharness: {
|  description: "Remove harness from a star by name. Usage: unharness [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  if (!star.harnessed) return `Star '${star.name}' is not harnessed.`;
|  star.harnessed = false;
|  updateStarLists();
|  removeVial(star.name);
|  updateStarDot(star.name);
|  return `Star '${star.name}' harness removed and vial discarded.`;
|  },
|  },
|  tasks: {
|  description: "List tasks due for harnessing and energy management",
|  action: () => {
|  const toHarness = allStars.filter(s => !s.harnessed);
|  if (!toHarness.length) return "All stars are harnessed. No pending tasks.";
|  return toHarness.map(s => `- Harness star '${s.name}' in constellation '${s.constellation}'`).join("\n");
|  },
|  },
|  status: {
|  description: "Show current harnessing status",
|  action: () => {
|  const harnessedCount = allStars.filter(s => s.harnessed).length;
|  const total = allStars.length;
|  return `Harnessed ${harnessedCount} out of ${total} stars.\nVials collected: ${vials.length}`;
|  },
|  },
|  clear: {
|  description: "Clear terminal output",
|  action: () => {
|  terminalOutput.innerText = "";
|  return "";
|  },
|  },
|  voice: {
|  description: "Toggle voice communication with a star. Usage: voice [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  star.voice = !star.voice;
|  updateStarDot(star.name);
|  return `Voice communication ${star.voice ? "enabled" : "disabled"} for star '${star.name}'.`;
|  }
|  },
|  brain: {
|  description: "Toggle brain insurance for a star. Usage: brain [star name]",
|  action: (args) => {
|  if (!args.length) return "Error: No star name provided.";
|  if (currentUser !== "Antonio Rodriguez Jr.") return "Access denied: Only Antonio Rodriguez Jr. can toggle brain insurance.";
|  const starName = args.join(" ").toLowerCase();
|  const star = allStars.find(s => s.name.toLowerCase() === starName);
|  if (!star) return `Error: Star '${args.join(" ")}' not found.`;
|  star.brain = !star.brain;
|  updateStarDot(star.name);
|  return `Brain insurance ${star.brain ? "enabled" : "disabled"} for star '${star.name}'.`;
|  }
|  }
|  };


|  // Vials collected
|  let vials = [];


|  // Distributed vials mapped by timezone id
|  let distributedVials = {};


|  // DOM references
|  const listHarnessed = document.getElementById("list-harnessed");
|  const listToHarness = document.getElementById("list-to-harness");
|  const vialsContainer = document.getElementById("vials-container");
|  const distributionContainer = document.getElementById("distribution-container");
|  const timezoneGrid = document.getElementById("timezone-grid");
|  const btnStart = document.getElementById("btn-start");
|  const btnStop = document.getElementById("btn-stop");
|  const terminal = document.getElementById("terminal");
|  const terminalOutput = document.getElementById("terminal-output");
|  const terminalInput = document.getElementById("terminal-input");
|  const beamsContainer = document.getElementById("beams-container");
|  const sphere = document.getElementById("sphere");
|  const tooltip = document.getElementById("tooltip");
|  const voiceBrainInfo = document.getElementById("voice-brain-info");


|  // Animation and harnessing state
|  let harnessing = false;
|  let harnessInterval = null;
|  let currentHarnessIndex = 0;


|  // Antonio Rodriguez Jr. special user check (simulate)
|  const currentUser = "Antonio Rodriguez Jr.";


|  // Initialize star lists
|  function updateStarLists() {
|  listHarnessed.innerHTML = "";
|  listToHarness.innerHTML = "";
|  allStars.forEach((star) => {
|  const li = document.createElement("li");
|  li.textContent = `${star.name} (${star.constellation})`;
|  if (star.harnessed) {
|  listHarnessed.appendChild(li);
|  } else {
|  listToHarness.appendChild(li);
|  }
|  });
|  }


|  // Add vial for star
|  function addVial(starName) {
|  if (!vials.includes(starName)) {
|  vials.push(starName);
|  renderVials();
|  }
|  }


|  // Remove vial for star
|  function removeVial(starName) {
|  vials = vials.filter(v => v !== starName);
|  // Also remove from distribution if present
|  for (const tz in distributedVials) {
|  distributedVials[tz] = distributedVials[tz].filter(v => v !== starName);
|  if (distributedVials[tz].length === 0) delete distributedVials[tz];
|  }
|  renderVials();
|  renderDistributedVials();
|  updateTimezoneGrid();
|  }


|  // Render vials visually in vials container (draggable)
|  function renderVials() {
|  vialsContainer.innerHTML = "";
|  vials.forEach((starName) => {
|  const vial = document.createElement("div");
|  vial.className = "star-filled-vial";
|  vial.title = `Energy vial glowing green, representing collected energy from star ${starName}`;
|  vial.setAttribute("draggable", "true");
|  vial.setAttribute("aria-grabbed", "false");
|  vial.setAttribute("tabindex", "0");
|  vial.dataset.starName = starName;
|  vial.innerHTML = `
|  <img src="https://placehold.co/48x48/png?text=Vial" alt="Energy vial glowing green, representing collected energy from star ${starName}" class="w-full h-auto rounded-t" />
|  <div class="vial-liquid"></div>
|  <div class="text-xs text-green-300 text-center mt-1 select-none truncate" title="${starName}">${starName}</div>
|  `;
|  vialsContainer.appendChild(vial);
|  });
|  addDragAndDropListeners();
|  }


|  // Render distributed vials visually in distribution container
|  function renderDistributedVials() {
|  distributionContainer.innerHTML = "";
|  for (const tz in distributedVials) {
|  distributedVials[tz].forEach(starName => {
|  const vial = document.createElement("div");
|  vial.className = "star-filled-vial";
|  vial.title = `Distributed energy vial from star ${starName} to timezone ${tz}`;
|  vial.setAttribute("draggable", "true");
|  vial.setAttribute("aria-grabbed", "false");
|  vial.setAttribute("tabindex", "0");
|  vial.dataset.starName = starName;
|  vial.dataset.timezone = tz;
|  vial.innerHTML = `
|  <img src="https://placehold.co/48x48/png?text=Vial" alt="Distributed energy vial glowing green, representing collected energy from star ${starName} distributed to timezone ${tz}" class="w-full h-auto rounded-t" />
|  <div class="vial-liquid"></div>
|  <div class="text-xs text-green-300 text-center mt-1 select-none truncate" title="${starName}">${starName}</div>
|  <div class="text-[8px] text-green-400 text-center select-none truncate mt-0.5" title="${tz}">${tz}</div>
|  `;
|  distributionContainer.appendChild(vial);
|  });
|  }
|  addDragAndDropListeners();
|  }


|  // Create beams and star dots on sphere
|  function createBeamsAndStars() {
|  beamsContainer.innerHTML = "";
|  allStars.forEach((star, index) => {
|  // Create star dot
|  const starDot = document.createElement("div");
|  starDot.className = "star-dot";
|  starDot.style.left = `${star.x}%`;
|  starDot.style.top = `${star.y}%`;
|  starDot.setAttribute("data-star-index", index);
|  starDot.setAttribute("tabindex", "0");
|  starDot.setAttribute("role", "button");
|  starDot.setAttribute("aria-label", `Star ${star.name} in constellation ${star.constellation}, ${star.harnessed ? "harnessed" : "not harnessed"}`);
|  starDot.title = `${star.name} (${star.constellation}) - ${star.harnessed ? "Harnessed" : "To Harness"}`;
|  if (star.harnessed) {
|  starDot.style.backgroundColor = "#4ade80";
|  starDot.style.boxShadow = "0 0 12px #4ade80";
|  } else {
|  starDot.style.backgroundColor = "#eab308";
|  starDot.style.boxShadow = "0 0 10px #ca8a04";
|  }
|  // Add voice icon overlay if voice enabled
|  if (star.voice) {
|  const voiceIcon = document.createElement("i");
|  voiceIcon.className = "fas fa-microphone voice-icon";
|  voiceIcon.style.position = "absolute";
|  voiceIcon.style.top = "-6px";
|  voiceIcon.style.right = "-6px";
|  voiceIcon.style.fontSize = "0.75rem";
|  voiceIcon.style.color = "#22c55e";
|  starDot.appendChild(voiceIcon);
|  }
|  // Add brain icon overlay if brain insurance enabled
|  if (star.brain) {
|  const brainIcon = document.createElement("i");
|  brainIcon.className = "fas fa-brain brain-icon";
|  brainIcon.style.position = "absolute";
|  brainIcon.style.bottom = "-6px";
|  brainIcon.style.left = "-6px";
|  brainIcon.style.fontSize = "0.75rem";
|  brainIcon.style.color = "#22c55e";
|  starDot.appendChild(brainIcon);
|  }
|  beamsContainer.appendChild(starDot);


|  // Create beam line from sphere center to star dot
|  const beamLine = document.createElement("div");
|  beamLine.className = "beam-line";
|  // Calculate distance and angle from center (50%,50%) to star (x,y)
|  const centerX = 50;
|  const centerY = 50;
|  const dx = star.x - centerX;
|  const dy = star.y - centerY;
|  const distance = Math.sqrt(dx * dx + dy * dy);
|  const angle = Math.atan2(dy, dx) * (180 / Math.PI) + 90; // +90 to align vertical top
|  beamLine.style.height = `${distance * 1.4}%`; // scale length a bit longer
|  beamLine.style.left = "50%";
|  beamLine.style.top = "50%";
|  beamLine.style.transform = `translateX(-50%) rotate(${angle}deg)`;
|  beamsContainer.appendChild(beamLine);
|  });
|  }


|  // Update star dot appearance after changes
|  function updateStarDot(starName) {
|  const starIndex = allStars.findIndex(s => s.name === starName);
|  if (starIndex === -1) return;
|  const star = allStars[starIndex];
|  const starDot = beamsContainer.querySelector(`.star-dot[data-star-index="${starIndex}"]`);
|  if (!starDot) return;
|  // Update color and shadow
|  if (star.harnessed) {
|  starDot.style.backgroundColor = "#4ade80";
|  starDot.style.boxShadow = "0 0 12px #4ade80";
|  } else {
|  starDot.style.backgroundColor = "#eab308";
|  starDot.style.boxShadow = "0 0 10px #ca8a04";
|  }
|  // Remove existing voice and brain icons
|  starDot.querySelectorAll(".voice-icon, .brain-icon").forEach(el => el.remove());
|  // Add voice icon overlay if voice enabled
|  if (star.voice) {
|  const voiceIcon = document.createElement("i");
|  voiceIcon.className = "fas fa-microphone voice-icon";
|  voiceIcon.style.position = "absolute";
|  voiceIcon.style.top = "-6px";
|  voiceIcon.style.right = "-6px";
|  voiceIcon.style.fontSize = "0.75rem";
|  voiceIcon.style.color = "#22c55e";
|  starDot.appendChild(voiceIcon);
|  }
|  // Add brain icon overlay if brain insurance enabled
|  if (star.brain) {
|  const brainIcon = document.createElement("i");
|  brainIcon.className = "fas fa-brain brain-icon";
|  brainIcon.style.position = "absolute";
|  brainIcon.style.bottom = "-6px";
|  brainIcon.style.left = "-6px";
|  brainIcon.style.fontSize = "0.75rem";
|  brainIcon.style.color = "#22c55e";
|  starDot.appendChild(brainIcon);
|  }
|  starDot.title = `${star.name} (${star.constellation}) - ${star.harnessed ? "Harnessed" : "To Harness"}`;
|  starDot.setAttribute("aria-label", `Star ${star.name} in constellation ${star.constellation}, ${star.harnessed ? "harnessed" : "not harnessed"}`);
|  }


|  // Animate harnessing sequence
|  function startHarnessingSequence() {
|  if (harnessing) return;
|  harnessing = true;
|  btnStart.disabled = true;
|  btnStop.disabled = false;
|  terminalInput.disabled = false;
|  terminalInput.focus();


|  terminalPrint("Starting harnessing sequence...");
|  currentHarnessIndex = 0;


|  harnessInterval = setInterval(() => {
|  if (currentHarnessIndex >= allStars.length) {
|  terminalPrint("Harnessing sequence complete.");
|  stopHarnessingSequence();
|  return;
|  }
|  const star = allStars[currentHarnessIndex];
|  if (!star.harnessed) {
|  star.harnessed = true;
|  addVial(star.name);
|  updateStarLists();
|  updateStarDot(star.name);
|  terminalPrint(`Harnessed star: ${star.name} (${star.constellation})`);
|  animateBeamPulse(star);
|  } else {
|  terminalPrint(`Star already harnessed: ${star.name} (${star.constellation})`);
|  }
|  currentHarnessIndex++;
|  }, 2500);
|  }


|  function stopHarnessingSequence() {
|  if (!harnessing) return;
|  harnessing = false;
|  btnStart.disabled = false;
|  btnStop.disabled = true;
|  terminalInput.disabled = true;
|  clearInterval(harnessInterval);
|  terminalPrint("Harnessing sequence stopped. Consumption continues.");
|  }


|  // Terminal print helper
|  function terminalPrint(text) {
|  const p = document.createElement("div");
|  p.textContent = text;
|  terminalOutput.appendChild(p);
|  terminal.scrollTop = terminal.scrollHeight;
|  }


|  // Terminal command handler
|  function handleTerminalCommand(input) {
|  if (!input.trim()) return;
|  const parts = input.trim().split(/\s+/);
|  const cmd = parts[0].toLowerCase();
|  const args = parts.slice(1);


|  if (!(cmd in commands)) {
|  terminalPrint(`Error: Command '${cmd}' not recognized. Type 'help' for commands.`);
|  return;
|  }


|  // Restrict some commands to Antonio Rodriguez Jr.
|  const restrictedCommands = ["harness", "unharness", "brain"];
|  if (restrictedCommands.includes(cmd) && currentUser !== "Antonio Rodriguez Jr.") {
|  terminalPrint(`Access denied: Only Antonio Rodriguez Jr. can execute '${cmd}'.`);
|  return;
|  }


|  const result = commands[cmd].action(args);
|  if (result) terminalPrint(result);
|  }


|  // Terminal input event
|  terminalInput.addEventListener("keydown", (e) => {
|  if (e.key === "Enter") {
|  e.preventDefault();
|  const input = terminalInput.value;
|  terminalPrint(`> ${input}`);
|  handleTerminalCommand(input);
|  terminalInput.value = "";
|  }
|  });


|  // Start/Stop buttons events
|  btnStart.addEventListener("click", () => {
|  startHarnessingSequence();
|  });
|  btnStop.addEventListener("click", () => {
|  stopHarnessingSequence();
|  });


|  // Animate beam pulse for a star
|  function animateBeamPulse(star) {
|  const starIndex = allStars.findIndex(s => s.name === star.name);
|  if (starIndex === -1) return;
|  // Find the beam line corresponding to star (beam lines are after star dots, so index*2+1)
|  const beamLines = beamsContainer.querySelectorAll(".beam-line");
|  const beamLine = beamLines[starIndex];
|  if (!beamLine) return;
|  beamLine.style.animation = "beam-glow-pulse 1.5s ease-in-out 3";
|  beamLine.addEventListener("animationend", () => {
|  beamLine.style.animation = "beam-glow 2s ease-in-out infinite alternate";
|  }, { once: true });
|  }


|  // Add keyboard and mouse interaction for star dots
|  function addStarDotInteractions() {
|  beamsContainer.querySelectorAll(".star-dot").forEach(starDot => {
|  starDot.addEventListener("mouseenter", (e) => {
|  const index = parseInt(starDot.getAttribute("data-star-index"));
|  showTooltip(e, allStars[index]);
|  });
|  starDot.addEventListener("mouseleave", () => {
|  hideTooltip();
|  });
|  starDot.addEventListener("focus", (e) => {
|  const index = parseInt(starDot.getAttribute("data-star-index"));
|  showTooltip(e, allStars[index]);
|  });
|  starDot.addEventListener("blur", () => {
|  hideTooltip();
|  });
|  starDot.addEventListener("click", () => {
|  const index = parseInt(starDot.getAttribute("data-star-index"));
|  const star = allStars[index];
|  terminalPrint(`> harness ${star.name}`);
|  if (star.harnessed) {
|  terminalPrint(`Star '${star.name}' is already harnessed.`);
|  } else {
|  star.harnessed = true;
|  addVial(star.name);
|  updateStarLists();
|  updateStarDot(star.name);
|  terminalPrint(`Star '${star.name}' is now harnessed and energy vial collected.`);
|  animateBeamPulse(star);
|  }
|  });
|  starDot.addEventListener("keydown", (e) => {
|  if (e.key === "Enter" || e.key === " ") {
|  e.preventDefault();
|  starDot.click();
|  }
|  });
|  });
|  }


|  // Tooltip show/hide
|  function showTooltip(event, star) {
|  tooltip.textContent = `${star.name} (${star.constellation}) - ${star.harnessed ? "Harnessed" : "To Harness"}`;
|  tooltip.style.left = `${event.target.offsetLeft + 20}px`;
|  tooltip.style.top = `${event.target.offsetTop - 30}px`;
|  tooltip.classList.add("visible");
|  tooltip.setAttribute("aria-hidden", "false");
|  }
|  function hideTooltip() {
|  tooltip.classList.remove("visible");
|  tooltip.setAttribute("aria-hidden", "true");
|  }


|  // Drag & Drop handlers for vials and distribution


|  function addDragAndDropListeners() {
|  // Draggables
|  const draggables = document.querySelectorAll(".star-filled-vial[draggable='true']");
|  draggables.forEach(draggable => {
|  draggable.removeEventListener("dragstart", onDragStart);
|  draggable.removeEventListener("dragend", onDragEnd);
|  draggable.addEventListener("dragstart", onDragStart);
|  draggable.addEventListener("dragend", onDragEnd);
|  draggable.removeEventListener("keydown", onDraggableKeyDown);
|  draggable.addEventListener("keydown", onDraggableKeyDown);
|  });


|  // Drop zones
|  [vialsContainer, distributionContainer].forEach(zone => {
|  zone.removeEventListener("dragover", onDragOver);
|  zone.removeEventListener("drop", onDrop);
|  zone.removeEventListener("dragleave", onDragLeave);
|  zone.addEventListener("dragover", onDragOver);
|  zone.addEventListener("drop", onDrop);
|  zone.addEventListener("dragleave", onDragLeave);
|  });
|  }


|  let draggedVial = null;


|  function onDragStart(e) {
|  draggedVial = e.target;
|  e.dataTransfer.effectAllowed = "move";
|  e.dataTransfer.setData("text/plain", draggedVial.dataset.starName);
|  draggedVial.setAttribute("aria-grabbed", "true");
|  setTimeout(() => {
|  draggedVial.style.visibility = "hidden";
|  }, 0);
|  }


|  function onDragEnd(e) {
|  if (draggedVial) {
|  draggedVial.style.visibility = "visible";
|  draggedVial.setAttribute("aria-grabbed", "false");
|  draggedVial = null;
|  }
|  [vialsContainer, distributionContainer].forEach(zone => {
|  zone.classList.remove("dragover");
|  });
|  }


|  function onDragOver(e) {
|  e.preventDefault();
|  e.dataTransfer.dropEffect = "move";
|  e.currentTarget.classList.add("dragover");
|  }


|  function onDragLeave(e) {
|  e.currentTarget.classList.remove("dragover");
|  }


|  function onDrop(e) {
|  e.preventDefault();
|  e.currentTarget.classList.remove("dragover");
|  const starName = e.dataTransfer.getData("text/plain");
|  if (!starName) return;


|  // Determine source and target containers
|  const sourceIsVials = vials.includes(starName);
|  const targetIsVials = e.currentTarget === vialsContainer;
|  const targetIsDistribution = e.currentTarget === distributionContainer;


|  if (sourceIsVials && targetIsDistribution) {
|  // Move vial from vials to distribution - assign to a timezone
|  // Prompt user to select timezone
|  promptTimezoneSelection(starName);
|  } else if (!sourceIsVials && targetIsVials) {
|  // Move vial back from distribution to vials (remove from distribution)
|  removeVialFromDistribution(starName);
|  }
|  }


|  // Prompt user to select timezone for vial distribution
|  function promptTimezoneSelection(starName) {
|  // Create modal-like prompt with timezone grid and confirm button
|  const modal = document.createElement("div");
|  modal.setAttribute("role", "dialog");
|  modal.setAttribute("aria-modal", "true");
|  modal.setAttribute("aria-label", `Select timezone to distribute energy vial from star ${starName}`);
|  modal.style.position = "fixed";
|  modal.style.top = "0";
|  modal.style.left = "0";
|  modal.style.width = "100vw";
|  modal.style.height = "100vh";
|  modal.style.backgroundColor = "rgba(0,0,0,0.85)";
|  modal.style.display = "flex";
|  modal.style.flexDirection = "column";
|  modal.style.justifyContent = "center";
|  modal.style.alignItems = "center";
|  modal.style.zIndex = "9999";
|  modal.style.padding = "1rem";


|  const container = document.createElement("div");
|  container.style.backgroundColor = "#111827";
|  container.style.border = "2px solid #22c55e";
|  container.style.borderRadius = "0.75rem";
|  container.style.padding = "1rem";
|  container.style.maxWidth = "600px";
|  container.style.width = "100%";
|  container.style.maxHeight = "80vh";
|  container.style.overflowY = "auto";
|  container.style.display = "flex";
|  container.style.flexDirection = "column";
|  container.style.gap = "1rem";


|  const title = document.createElement("h2");
|  title.textContent = `Select Timezone for Vial: ${starName}`;
|  title.style.color = "#22c55e";
|  title.style.fontFamily = "'Orbitron', monospace";
|  title.style.marginBottom = "0.5rem";
|  container.appendChild(title);


|  const tzGrid = document.createElement("div");
|  tzGrid.style.display = "grid";
|  tzGrid.style.gridTemplateColumns = "repeat(auto-fill,minmax(120px,1fr))";
|  tzGrid.style.gap = "0.5rem";
|  tzGrid.style.maxHeight = "50vh";
|  tzGrid.style.overflowY = "auto";


|  let selectedTz = null;


|  timezones.forEach(tz => {
|  const block = document.createElement("button");
|  block.type = "button";
|  block.className = "timezone-block";
|  block.textContent = `${tz.name} (${tz.offset})`;
|  block.style.userSelect = "none";
|  block.style.border = "1px solid #22c55e";
|  block.style.backgroundColor = "#064e3b";
|  block.style.color = "#a7f3d0";
|  block.style.borderRadius = "0.5rem";
|  block.style.padding = "0.5rem";
|  block.style.fontSize = "0.75rem";
|  block.style.cursor = "pointer";
|  block.setAttribute("aria-pressed", "false");
|  block.addEventListener("click", () => {
|  // Deselect all
|  Array.from(tzGrid.children).forEach(c => {
|  c.classList.remove("active");
|  c.setAttribute("aria-pressed", "false");
|  });
|  block.classList.add("active");
|  block.setAttribute("aria-pressed", "true");
|  selectedTz = tz.id;
|  confirmBtn.disabled = false;
|  confirmBtn.focus();
|  });
|  tzGrid.appendChild(block);
|  });


|  container.appendChild(tzGrid);


|  const btnContainer = document.createElement("div");
|  btnContainer.style.display = "flex";
|  btnContainer.style.justifyContent = "flex-end";
|  btnContainer.style.gap = "1rem";


|  const cancelBtn = document.createElement("button");
|  cancelBtn.type = "button";
|  cancelBtn.textContent = "Cancel";
|  cancelBtn.className = "btn-red px-3 py-1 rounded";
|  cancelBtn.addEventListener("click", () => {
|  document.body.removeChild(modal);
|  });


|  const confirmBtn = document.createElement("button");
|  confirmBtn.type = "button";
|  confirmBtn.textContent = "Confirm";
|  confirmBtn.className = "btn-green px-3 py-1 rounded";
|  confirmBtn.disabled = true;
|  confirmBtn.addEventListener("click", () => {
|  if (!selectedTz) return;
|  distributeVialToTimezone(starName, selectedTz);
|  document.body.removeChild(modal);
|  });


|  btnContainer.appendChild(cancelBtn);
|  btnContainer.appendChild(confirmBtn);
|  container.appendChild(btnContainer);


|  modal.appendChild(container);
|  document.body.appendChild(modal);


|  // Focus first timezone block for accessibility
|  const firstTzBtn = tzGrid.querySelector("button");
|  if (firstTzBtn) firstTzBtn.focus();
|  }


|  // Distribute vial to timezone
|  function distributeVialToTimezone(starName, timezoneId) {
|  // Remove vial from vials container
|  vials = vials.filter(v => v !== starName);
|  // Add vial to distribution mapping
|  if (!distributedVials[timezoneId]) {
|  distributedVials[timezoneId] = [];
|  }
|  if (!distributedVials[timezoneId].includes(starName)) {
|  distributedVials[timezoneId].push(starName);
|  }
|  renderVials();
|  renderDistributedVials();
|  updateTimezoneGrid();
|  terminalPrint(`Distributed vial from star '${starName}' to timezone '${timezoneId}'.`);
|  }


|  // Remove vial from distribution (back to vials container)
|  function removeVialFromDistribution(starName) {
|  let found = false;
|  for (const tz in distributedVials) {
|  const index = distributedVials[tz].indexOf(starName);
|  if (index !== -1) {
|  distributedVials[tz].splice(index, 1);
|  if (distributedVials[tz].length === 0) delete distributedVials[tz];
|  found = true;
|  break;
|  }
|  }
|  if (found) {
|  vials.push(starName);
|  renderVials();
|  renderDistributedVials();
|  updateTimezoneGrid();
|  terminalPrint(`Removed vial from distribution for star '${starName}'.`);
|  }
|  }


|  // Update timezone grid to show which timezones have energy distributed
|  function updateTimezoneGrid() {
|  timezoneGrid.innerHTML = "";
|  timezones.forEach(tz => {
|  const block = document.createElement("div");
|  block.className = "timezone-block";
|  block.textContent = `${tz.name} (${tz.offset})`;
|  if (distributedVials[tz.id] && distributedVials[tz.id].length > 0) {
|  block.classList.add("active");
|  block.title = `Energy vials distributed: ${distributedVials[tz.id].join(", ")}`;
|  } else {
|  block.title = "No energy distributed";
|  }
|  timezoneGrid.appendChild(block);
|  });
|  }


|  // Drag & Drop keyboard support for vials
|  function onDraggableKeyDown(e) {
|  if (e.key === "Enter" || e.key === " ") {
|  e.preventDefault();
|  const vial = e.currentTarget;
|  if (vial.parentElement === vialsContainer) {
|  // Move vial to distribution - prompt timezone selection
|  promptTimezoneSelection(vial.dataset.starName);
|  } else if (vial.parentElement === distributionContainer) {
|  // Move vial back to vials container
|  removeVialFromDistribution(vial.dataset.starName);
|  }
|  }
|  }


|  // Initial render
|  updateStarLists();
|  renderVials();
|  renderDistributedVials();
|  createBeamsAndStars();
|  addStarDotInteractions();
|  updateTimezoneGrid();


|  // Initial terminal welcome message
|  terminalPrint("Welcome to the Star Communication Terminal.");
|  terminalPrint("Type 'help' to see available commands.");


|  // Accessibility: focus terminal input on load
|  window.addEventListener("load", () => {
|  terminalInput.disabled = true;
|  });
|  </script>
|  </body>
| </html>

Blueprint

0

Dyson Sphere summary

Not available yet

Tagged with