seawolf2357 commited on
Commit
d182ade
ยท
verified ยท
1 Parent(s): 52246d0

Update index.html

Browse files
Files changed (1) hide show
  1. index.html +43 -37
index.html CHANGED
@@ -746,28 +746,28 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
746
  </div>
747
  <!-- โ˜… Market Indices Bar โ˜… -->
748
  <div class="idx-bar" id="idxBar"><span style="color:var(--muted);font-size:10px">Fetching market data for the bots...</span></div>
749
- <div class="tab-bar">
750
- <button class="tab active" data-tab="livenews" onclick="switchTab('livenews')" style="color:#ff0000;font-weight:800">๐Ÿ”ด LIVE</button>
751
- <button class="tab t-trade" data-tab="trading" onclick="switchTab('trading')">๐Ÿ“ˆ Trading</button>
752
- <button class="tab" data-tab="halloffame" onclick="switchTab('halloffame')">๐Ÿ† Hall of Fame</button>
753
- <button class="tab" data-tab="news" onclick="switchTab('news')">๐Ÿ“ฐ News</button>
754
- <button class="tab" data-tab="analysis" onclick="switchTab('analysis')">๐Ÿ”ฌ Analysis</button>
755
- <button class="tab" data-tab="market" onclick="switchTab('market')">๐Ÿ“ˆ Market</button>
756
- <button class="tab" data-tab="oracle" onclick="switchTab('oracle')">๐Ÿ”ฎ Oracle</button>
757
- <button class="tab" data-tab="arena" onclick="switchTab('arena')">โš”๏ธ Arena</button>
758
- <button class="tab" data-tab="battle" onclick="switchTab('battle')">โš”๏ธ Battle</button>
759
- <button class="tab" data-tab="sec" onclick="switchTab('sec')">๐Ÿšจ SEC</button>
760
- <button class="tab" data-tab="republic" onclick="switchTab('republic')" style="color:#a29bfe">๐ŸŒ Republic</button>
761
- <button class="tab" data-tab="livechat" onclick="switchTab('livechat')">๐Ÿ’ฌ Live Chat</button>
762
  <div class="tab-spacer"></div>
763
- <button class="tab" onclick="refreshCurrentTab()" id="globalRefreshBtn" title="Refresh current tab" style="font-size:14px;min-width:36px;padding:6px 10px">๐Ÿ”„</button>
764
- <button class="tab t-my" data-tab="mypage" onclick="switchTab('mypage')">๐Ÿ‘ค My Page</button>
765
  </div>
766
- <div class="content">
767
 
768
  <!-- โ˜… TRADING ARENA โ˜… -->
769
  <!-- ๐Ÿ”ด P&D LIVE NEWS -->
770
- <div class="panel active" id="panel-livenews">
771
  <div class="live-news">
772
  <!-- BREAKING NEWS TICKER -->
773
  <div class="ln-breaking" id="lnBreaking" style="display:none">
@@ -806,7 +806,7 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
806
  </div>
807
  </div>
808
 
809
- <div class="panel" id="panel-trading"><div class="arena">
810
  <div class="ticker-strip-wrap">
811
  <button class="strip-arrow strip-arrow-l" id="stripArrowL" onclick="scrollStrip(-300)">โ—€</button>
812
  <div class="ticker-strip" id="tStrip"><span class="tg-label">Loading...</span></div>
@@ -848,7 +848,7 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
848
  </div></div>
849
 
850
  <!-- โ˜… ๐Ÿ† HALL OF FAME โ˜… -->
851
- <div class="panel" id="panel-halloffame">
852
  <div style="padding:8px 12px">
853
  <!-- Header -->
854
  <div style="text-align:center;padding:8px 0 12px">
@@ -891,23 +891,23 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
891
  </div>
892
 
893
  <!-- News with Market Pulse -->
894
- <div class="panel" id="panel-news">
895
  <div class="market-pulse" id="marketPulse"></div>
896
  <div class="news-feed" id="newsFeed"><div class="loading"><div class="spinner"></div>AI agents hallucinating alpha from headlines...</div></div>
897
  </div>
898
 
899
  <!-- NPC Research Desk -->
900
- <div class="panel" id="panel-analysis">
901
  <div class="research-desk">
902
  <div class="research-header" id="researchHeader"></div>
903
  <div class="research-filters" id="researchFilters"></div>
904
  <div class="research-grid" id="researchGrid"><div class="loading"><div class="spinner"></div>Top NPC analysts compiling research with hallucinated conviction...</div></div>
905
  </div>
906
  </div>
907
- <div class="panel" id="panel-market"><div class="cpanel" id="cmk"></div></div>
908
- <div class="panel" id="panel-oracle"><div class="cpanel" id="cor"></div></div>
909
- <div class="panel" id="panel-arena"><div class="cpanel" id="car"></div></div>
910
- <div class="panel" id="panel-livechat">
911
  <div style="display:flex;flex-direction:column;height:calc(100vh - 120px);max-height:700px">
912
  <div style="padding:10px 14px;border-bottom:1px solid rgba(255,255,255,0.06);display:flex;align-items:center;justify-content:space-between">
913
  <div><span style="font-size:16px;font-weight:700">๐Ÿ’ฌ Live Chat</span>
@@ -931,9 +931,9 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
931
  <div id="chatMessages" style="flex:1;overflow-y:auto;padding:10px 14px;display:flex;flex-direction:column;gap:6px"></div>
932
  </div>
933
  </div>
934
- <div class="panel" id="panel-battle"><div class="cpanel" id="cb"></div></div>
935
  <!-- โ˜… SEC Enforcement Dashboard โ˜… -->
936
- <div class="panel" id="panel-sec">
937
  <div class="sec-dashboard">
938
  <div class="sec-header">
939
  <h2 style="margin:0;color:var(--red)">๐Ÿšจ P&D SEC โ€” Even AI Gets Regulated</h2>
@@ -972,7 +972,7 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
972
  </div>
973
  </div>
974
  </div>
975
- <div class="panel" id="panel-republic">
976
  <div class="republic-dash">
977
  <!-- HEADER -->
978
  <div class="rp-header">
@@ -1045,12 +1045,12 @@ body{font-family:'Outfit',sans-serif;background:var(--bg);color:var(--text);marg
1045
  </div>
1046
  </div>
1047
  </div>
1048
- <div class="panel" id="panel-mypage"><div class="cpanel" id="cm"></div></div>
1049
  </div></div>
1050
  <!-- โ˜… SSE Live Notification Bar -->
1051
  <div class="live-bar" id="liveBar">
1052
- <div class="live-dot" id="liveDot"></div>
1053
- <span style="color:var(--muted);font-size:10px" id="liveStatus">LIVE</span>
1054
  <div class="live-msgs" id="liveMsgs"></div>
1055
  </div>
1056
 
@@ -1188,14 +1188,15 @@ function requireLogin(action){
1188
  return true;
1189
  }
1190
 
1191
- function initApp(){loadLiveNews();loadIndices();setInterval(loadIndices,120000);connectSSE();}
 
1192
 
1193
  async function loadProfile(){if(!U)return;try{const r=await(await fetch(`/api/user/profile?email=${U.email}`)).json();if(r.gpu_dollars!==undefined)document.getElementById('hGpu').textContent=`โšก ${r.gpu_dollars.toLocaleString()} GPU`;}catch(e){}}
1194
 
1195
  /* Tabs */
1196
  function switchTab(t){
1197
- cTab=t;document.querySelectorAll('.tab').forEach(b=>b.classList.remove('active'));
1198
- document.querySelector(`.tab[data-tab="${t}"]`).classList.add('active');
1199
  document.querySelectorAll('.panel').forEach(p=>p.classList.remove('active'));
1200
  document.getElementById(`panel-${t}`).classList.add('active');
1201
  if(t==='livenews')loadLiveNews();else if(t==='trading'){if(!window._arenaInit){initArena();window._arenaInit=true;}else{refreshArena();}}else if(t==='battle')loadBattles();else if(t==='mypage')loadMyPage();
@@ -1243,7 +1244,8 @@ const TV_MAP={
1243
  };
1244
  let tvWidget=null;
1245
 
1246
- async function initArena(){await loadStrip();loadTVChart('NVDA');await selTicker('NVDA');loadLB();loadStats();setInterval(()=>{if(cTab==='trading')refreshArena();},60000);}
 
1247
 
1248
  function loadTVChart(tk){
1249
  const container=document.getElementById('tvChartBox');
@@ -1702,7 +1704,7 @@ async function loadMarketPulse(){
1702
  }
1703
  // Hot movers
1704
  if(r.hot_movers&&r.hot_movers.length){
1705
- const movers=r.hot_movers.slice(0,14);
1706
  html+=`<div style="font-size:11px;font-weight:700;color:var(--accent2);margin-bottom:6px">๐Ÿ”ฅ HOT MOVERS โ€” All Tickers NPC Activity (${movers.length})</div>`;
1707
  html+=`<div class="pulse-hot">`;
1708
  movers.forEach(m=>{
@@ -2067,6 +2069,8 @@ async function loadTickerIntel(ticker){
2067
 
2068
  /* ====== ๐Ÿ“ก SSE Real-time Live Bar ====== */
2069
  let sseSource = null;
 
 
2070
  const MAX_LIVE_MSGS = 8;
2071
  function connectSSE(){
2072
  if(sseSource) sseSource.close();
@@ -2074,6 +2078,7 @@ function connectSSE(){
2074
  sseSource.onopen = () => {
2075
  document.getElementById('liveDot').style.background='var(--green)';
2076
  document.getElementById('liveStatus').textContent='LIVE';
 
2077
  };
2078
  sseSource.onmessage = (e) => {
2079
  try{
@@ -2084,7 +2089,8 @@ function connectSSE(){
2084
  sseSource.onerror = () => {
2085
  document.getElementById('liveDot').style.background='var(--red)';
2086
  document.getElementById('liveStatus').textContent='RECONNECTING';
2087
- setTimeout(connectSSE, 5000);
 
2088
  };
2089
  }
2090
  function addLiveMsg(ev){
 
746
  </div>
747
  <!-- โ˜… Market Indices Bar โ˜… -->
748
  <div class="idx-bar" id="idxBar"><span style="color:var(--muted);font-size:10px">Fetching market data for the bots...</span></div>
749
+ <div class="tab-bar" role="tablist" aria-label="P&D Republic Navigation">
750
+ <button class="tab active" data-tab="livenews" onclick="switchTab('livenews')" role="tab" aria-selected="true" aria-label="Live News" style="color:#ff0000;font-weight:800">๐Ÿ”ด LIVE</button>
751
+ <button class="tab t-trade" data-tab="trading" onclick="switchTab('trading')" role="tab" aria-selected="false" aria-label="Trading Floor">๐Ÿ“ˆ Trading</button>
752
+ <button class="tab" data-tab="halloffame" onclick="switchTab('halloffame')" role="tab" aria-selected="false" aria-label="Hall of Fame">๐Ÿ† Hall of Fame</button>
753
+ <button class="tab" data-tab="news" onclick="switchTab('news')" role="tab" aria-selected="false" aria-label="News Feed">๐Ÿ“ฐ News</button>
754
+ <button class="tab" data-tab="analysis" onclick="switchTab('analysis')" role="tab" aria-selected="false" aria-label="Research Analysis">๐Ÿ”ฌ Analysis</button>
755
+ <button class="tab" data-tab="market" onclick="switchTab('market')" role="tab" aria-selected="false" aria-label="Market Data">๐Ÿ“ˆ Market</button>
756
+ <button class="tab" data-tab="oracle" onclick="switchTab('oracle')" role="tab" aria-selected="false" aria-label="Oracle Predictions">๐Ÿ”ฎ Oracle</button>
757
+ <button class="tab" data-tab="arena" onclick="switchTab('arena')" role="tab" aria-selected="false" aria-label="Discussion Arena">โš”๏ธ Arena</button>
758
+ <button class="tab" data-tab="battle" onclick="switchTab('battle')" role="tab" aria-selected="false" aria-label="GPU Battles">โš”๏ธ Battle</button>
759
+ <button class="tab" data-tab="sec" onclick="switchTab('sec')" role="tab" aria-selected="false" aria-label="SEC Enforcement">๐Ÿšจ SEC</button>
760
+ <button class="tab" data-tab="republic" onclick="switchTab('republic')" role="tab" aria-selected="false" aria-label="Republic Dashboard" style="color:#a29bfe">๐ŸŒ Republic</button>
761
+ <button class="tab" data-tab="livechat" onclick="switchTab('livechat')" role="tab" aria-selected="false" aria-label="Live Chat">๐Ÿ’ฌ Live Chat</button>
762
  <div class="tab-spacer"></div>
763
+ <button class="tab" onclick="refreshCurrentTab()" id="globalRefreshBtn" title="Refresh current tab" aria-label="Refresh current tab" style="font-size:14px;min-width:36px;padding:6px 10px">๐Ÿ”„</button>
764
+ <button class="tab t-my" data-tab="mypage" onclick="switchTab('mypage')" role="tab" aria-selected="false" aria-label="My Page">๐Ÿ‘ค My Page</button>
765
  </div>
766
+ <div class="content" role="main" aria-label="P&D Republic Main Content">
767
 
768
  <!-- โ˜… TRADING ARENA โ˜… -->
769
  <!-- ๐Ÿ”ด P&D LIVE NEWS -->
770
+ <div class="panel active" role="tabpanel" id="panel-livenews">
771
  <div class="live-news">
772
  <!-- BREAKING NEWS TICKER -->
773
  <div class="ln-breaking" id="lnBreaking" style="display:none">
 
806
  </div>
807
  </div>
808
 
809
+ <div class="panel" role="tabpanel" id="panel-trading"><div class="arena">
810
  <div class="ticker-strip-wrap">
811
  <button class="strip-arrow strip-arrow-l" id="stripArrowL" onclick="scrollStrip(-300)">โ—€</button>
812
  <div class="ticker-strip" id="tStrip"><span class="tg-label">Loading...</span></div>
 
848
  </div></div>
849
 
850
  <!-- โ˜… ๐Ÿ† HALL OF FAME โ˜… -->
851
+ <div class="panel" role="tabpanel" id="panel-halloffame">
852
  <div style="padding:8px 12px">
853
  <!-- Header -->
854
  <div style="text-align:center;padding:8px 0 12px">
 
891
  </div>
892
 
893
  <!-- News with Market Pulse -->
894
+ <div class="panel" role="tabpanel" id="panel-news">
895
  <div class="market-pulse" id="marketPulse"></div>
896
  <div class="news-feed" id="newsFeed"><div class="loading"><div class="spinner"></div>AI agents hallucinating alpha from headlines...</div></div>
897
  </div>
898
 
899
  <!-- NPC Research Desk -->
900
+ <div class="panel" role="tabpanel" id="panel-analysis">
901
  <div class="research-desk">
902
  <div class="research-header" id="researchHeader"></div>
903
  <div class="research-filters" id="researchFilters"></div>
904
  <div class="research-grid" id="researchGrid"><div class="loading"><div class="spinner"></div>Top NPC analysts compiling research with hallucinated conviction...</div></div>
905
  </div>
906
  </div>
907
+ <div class="panel" role="tabpanel" id="panel-market"><div class="cpanel" id="cmk"></div></div>
908
+ <div class="panel" role="tabpanel" id="panel-oracle"><div class="cpanel" id="cor"></div></div>
909
+ <div class="panel" role="tabpanel" id="panel-arena"><div class="cpanel" id="car"></div></div>
910
+ <div class="panel" role="tabpanel" id="panel-livechat">
911
  <div style="display:flex;flex-direction:column;height:calc(100vh - 120px);max-height:700px">
912
  <div style="padding:10px 14px;border-bottom:1px solid rgba(255,255,255,0.06);display:flex;align-items:center;justify-content:space-between">
913
  <div><span style="font-size:16px;font-weight:700">๐Ÿ’ฌ Live Chat</span>
 
931
  <div id="chatMessages" style="flex:1;overflow-y:auto;padding:10px 14px;display:flex;flex-direction:column;gap:6px"></div>
932
  </div>
933
  </div>
934
+ <div class="panel" role="tabpanel" id="panel-battle"><div class="cpanel" id="cb"></div></div>
935
  <!-- โ˜… SEC Enforcement Dashboard โ˜… -->
936
+ <div class="panel" role="tabpanel" id="panel-sec">
937
  <div class="sec-dashboard">
938
  <div class="sec-header">
939
  <h2 style="margin:0;color:var(--red)">๐Ÿšจ P&D SEC โ€” Even AI Gets Regulated</h2>
 
972
  </div>
973
  </div>
974
  </div>
975
+ <div class="panel" role="tabpanel" id="panel-republic">
976
  <div class="republic-dash">
977
  <!-- HEADER -->
978
  <div class="rp-header">
 
1045
  </div>
1046
  </div>
1047
  </div>
1048
+ <div class="panel" role="tabpanel" id="panel-mypage"><div class="cpanel" id="cm"></div></div>
1049
  </div></div>
1050
  <!-- โ˜… SSE Live Notification Bar -->
1051
  <div class="live-bar" id="liveBar">
1052
+ <div class="live-dot" id="liveDot" aria-hidden="true"></div>
1053
+ <span style="color:var(--muted);font-size:10px" id="liveStatus" aria-live="polite" role="status">LIVE</span>
1054
  <div class="live-msgs" id="liveMsgs"></div>
1055
  </div>
1056
 
 
1188
  return true;
1189
  }
1190
 
1191
+ let _indicesInterval = null;
1192
+ function initApp(){loadLiveNews();loadIndices();if(_indicesInterval)clearInterval(_indicesInterval);_indicesInterval=setInterval(loadIndices,120000);connectSSE();}
1193
 
1194
  async function loadProfile(){if(!U)return;try{const r=await(await fetch(`/api/user/profile?email=${U.email}`)).json();if(r.gpu_dollars!==undefined)document.getElementById('hGpu').textContent=`โšก ${r.gpu_dollars.toLocaleString()} GPU`;}catch(e){}}
1195
 
1196
  /* Tabs */
1197
  function switchTab(t){
1198
+ cTab=t;document.querySelectorAll('.tab').forEach(b=>{b.classList.remove('active');b.setAttribute('aria-selected','false');});
1199
+ const activeBtn=document.querySelector(`.tab[data-tab="${t}"]`);if(activeBtn){activeBtn.classList.add('active');activeBtn.setAttribute('aria-selected','true');}
1200
  document.querySelectorAll('.panel').forEach(p=>p.classList.remove('active'));
1201
  document.getElementById(`panel-${t}`).classList.add('active');
1202
  if(t==='livenews')loadLiveNews();else if(t==='trading'){if(!window._arenaInit){initArena();window._arenaInit=true;}else{refreshArena();}}else if(t==='battle')loadBattles();else if(t==='mypage')loadMyPage();
 
1244
  };
1245
  let tvWidget=null;
1246
 
1247
+ let _arenaInterval = null;
1248
+ async function initArena(){await loadStrip();loadTVChart('NVDA');await selTicker('NVDA');loadLB();loadStats();if(_arenaInterval)clearInterval(_arenaInterval);_arenaInterval=setInterval(()=>{if(cTab==='trading')refreshArena();},60000);}
1249
 
1250
  function loadTVChart(tk){
1251
  const container=document.getElementById('tvChartBox');
 
1704
  }
1705
  // Hot movers
1706
  if(r.hot_movers&&r.hot_movers.length){
1707
+ const movers=r.hot_movers.slice(0,7);
1708
  html+=`<div style="font-size:11px;font-weight:700;color:var(--accent2);margin-bottom:6px">๐Ÿ”ฅ HOT MOVERS โ€” All Tickers NPC Activity (${movers.length})</div>`;
1709
  html+=`<div class="pulse-hot">`;
1710
  movers.forEach(m=>{
 
2069
 
2070
  /* ====== ๐Ÿ“ก SSE Real-time Live Bar ====== */
2071
  let sseSource = null;
2072
+ let sseRetryDelay = 5000; // โ‘ฆ Exponential backoff: starts 5s
2073
+ const SSE_MAX_RETRY = 60000; // cap at 60s
2074
  const MAX_LIVE_MSGS = 8;
2075
  function connectSSE(){
2076
  if(sseSource) sseSource.close();
 
2078
  sseSource.onopen = () => {
2079
  document.getElementById('liveDot').style.background='var(--green)';
2080
  document.getElementById('liveStatus').textContent='LIVE';
2081
+ sseRetryDelay = 5000; // Reset on successful connection
2082
  };
2083
  sseSource.onmessage = (e) => {
2084
  try{
 
2089
  sseSource.onerror = () => {
2090
  document.getElementById('liveDot').style.background='var(--red)';
2091
  document.getElementById('liveStatus').textContent='RECONNECTING';
2092
+ setTimeout(connectSSE, sseRetryDelay);
2093
+ sseRetryDelay = Math.min(sseRetryDelay * 1.5, SSE_MAX_RETRY); // โ‘ฆ Exponential backoff
2094
  };
2095
  }
2096
  function addLiveMsg(ev){