{"id":1333,"date":"2026-04-20T08:05:51","date_gmt":"2026-04-20T08:05:51","guid":{"rendered":"https:\/\/thefiniteearth.org\/?page_id=1333"},"modified":"2026-05-15T08:02:05","modified_gmt":"2026-05-15T08:02:05","slug":"testing","status":"publish","type":"page","link":"https:\/\/thefiniteearth.org\/hindi\/testing\/","title":{"rendered":"Testing"},"content":{"rendered":"<p>Energy Swaraj Yatra                                                                                                                                                            Bharat Climate Satyagraha Yatra      100 Days Sacred Journey Across Bharat \u2014 Golden Quadrilateral                        <span>May 13 \u2013 Aug 20, 2026<\/span>        Day \u2014 of 100                <span>Today&#8217;s Schedule<\/span>                    <span>Invite Yatra<\/span>                  Journey Stats                                                                                                0                    Days Done                                                                                          100                    Days Left                                      KMs Covered          0                                              People Met          0                                                      <span id=\"live-txt\">LIVE<\/span>          Day \u2014                Loading\u2026        \u2014                    Next Stop        \u2014        \u2014                    Yatra Progress                Loading\u2026                    Route        Loading route\u2026                                                  <span>Currently at<\/span>      <span id=\"map-badge-city\">\u2014<\/span>                  India Route Map              <img decoding=\"async\" src=\"http:\/\/thefiniteearth.org\/wp-content\/uploads\/2026\/04\/Asset-1.png.webp\" alt=\"India Map\" style=\"width: 100%; display: block; border-radius: 10px; transition: transform 0.3s; transform: scale(1);\" onmouseover=\"this.style.transform='scale(1.02)'\" onmouseout=\"this.style.transform='scale(1)'\" onerror=\"this.closest('div').style.display='none'\">        <img decoding=\"async\" role=\"img\" alt=\"\ud83d\udd0d\" src=\"https:\/\/s.w.org\/images\/core\/emoji\/17.0.2\/svg\/1f50d.svg\"> Full View                    Schedule                  <\/p>\n<h2 id=\"cal-evt-title\">Event Details<\/h2>\n<p>\u00d7    No event data          <a id=\"yatra-invite\" href=\"javascript:void(0)\" onclick=\"closeCalEvt();closeDash();inviteYatra();\">                Take Action &#8211; Invite Yatra Now!      <\/a>                  <\/p>\n<h1>Live Yatra Tracking System<\/h1>\n<p>      \u2715 Close        Current City: <strong id=\"d-current-city-text\">Loading&#8230;<\/strong>                   Map                                                         Calendar                                    <span onclick=\"closeDEvt()\">\u00d7<\/span><\/p>\n<h2 id=\"d-modal-name\">Event Details<\/h2>\n<p>                  <span>Hosted By<\/span>          <span>Location<\/span><span id=\"d-modal-venue\"><\/span>, <span id=\"d-modal-city\"><\/span>                      <span>Date<\/span>            <span>Time<\/span>                    <span>Description<\/span>                          <a href=\"javascript:void(0)\" onclick=\"closeDEvt();closeDash();inviteYatra();\">                        Take Action &#8211; Invite Yatra Now!          <\/a>                          \u2715    <img decoding=\"async\" src=\"http:\/\/thefiniteearth.org\/wp-content\/uploads\/2026\/04\/Asset-1.png.webp\" alt=\"India Route Map\" style=\"max-width:100%;max-height:80vh;border-radius:8px;display:block;\">    Golden Quadrilateral Yatra Route \u2014 Bharat  [tcb-script src=&#8221;https:\/\/cdn.jsdelivr.net\/npm\/fullcalendar@5.11.3\/main.min.js&#8221;][\/tcb-script][tcb-script src=&#8221;https:\/\/cdnjs.cloudflare.com\/ajax\/libs\/d3\/7.9.0\/d3.min.js&#8221;][\/tcb-script][tcb-script]if (&#8216;scrollRestoration&#8217; in history) history.scrollRestoration = &#8216;manual&#8217;;\/\/ Remove any hash from URL on load to prevent scrolling to #take-actionif(window.location.hash) { history.replaceState(null, &#8221;, window.location.pathname + window.location.search); }window.scrollTo(0,0);document.addEventListener(&#8216;DOMContentLoaded&#8217;,()=&gt;{ window.scrollTo(0,0); });window.addEventListener(&#8216;load&#8217;,()=&gt;{ window.scrollTo(0,0); setTimeout(()=&gt;window.scrollTo(0,0),200); });function inviteYatra(){console.log(&#8220;hello&#8221;);    var target = document.getElementById(&#8220;take-action-invite-yatra-now&#8221;);        if (target) {        window.scrollTo({            top: target.offsetTop,            behavior: &#8220;smooth&#8221;        });    }  try{    \/\/ Try direct element scroll in parent window    var topDoc=window.top.document;    var el=topDoc.getElementById(&#8216;take-action-invite-yatra-now&#8217;);    if(el){el.scrollIntoView({behavior:&#8217;smooth&#8217;,block:&#8217;start&#8217;});return;}    \/\/ Try anchor link approach &#8211; does not reload page    var a=topDoc.createElement(&#8216;a&#8217;);    a.href=&#8217;#take-action-invite-yatra-now&#8217;;    topDoc.body.appendChild(a);    a.click();    topDoc.body.removeChild(a);  }catch(e){    \/\/ cross-origin: open same page at anchor in same tab    window.top.location.href=&#8217;https:\/\/thefiniteearth.org\/100-days-esy\/?preview=true#take-action-invite-yatra-now&#8217;;  }}const API_URL=&#8217;https:\/\/script.google.com\/macros\/s\/AKfycbwG5S7pytIy4PYRNluekHx8wgn6VPfqI9FJdOHoonbX9CrSO56IL8MGUikkq1V-wALq4w\/exec&#8217;;const GQ_ROUTE=[  {name:&#8217;Delhi&#8217;,lat:28.6139,lon:77.2090},{name:&#8217;Gurugram&#8217;,lat:28.4595,lon:77.0266},  {name:&#8217;Manesar&#8217;,lat:28.3562,lon:76.9383},{name:&#8217;Neemrana&#8217;,lat:27.9747,lon:76.3844},  {name:&#8217;Alwar&#8217;,lat:27.5530,lon:76.6346},{name:&#8217;Jaipur&#8217;,lat:26.9124,lon:75.7873},  {name:&#8217;Ajmer&#8217;,lat:26.4499,lon:74.6399},{name:&#8217;Bhilwara&#8217;,lat:25.3474,lon:74.6339},  {name:&#8217;Chittorgarh&#8217;,lat:24.8887,lon:74.6269},{name:&#8217;Udaipur&#8217;,lat:24.5854,lon:73.7125},  {name:&#8217;Ahmedabad&#8217;,lat:23.0225,lon:72.5714},{name:&#8217;Vadodara&#8217;,lat:22.3072,lon:73.1812},  {name:&#8217;Bharuch&#8217;,lat:21.7051,lon:72.9959},{name:&#8217;Surat&#8217;,lat:21.1702,lon:72.8311},  {name:&#8217;Vapi&#8217;,lat:20.3749,lon:72.9057},{name:&#8217;Mumbai&#8217;,lat:19.0760,lon:72.8777},  {name:&#8217;Pune&#8217;,lat:18.5204,lon:73.8567},{name:&#8217;Satara&#8217;,lat:17.6805,lon:74.0183},  {name:&#8217;Kolhapur&#8217;,lat:16.7050,lon:74.2433},{name:&#8217;Belagavi&#8217;,lat:15.8497,lon:74.4977},  {name:&#8217;Dharwad&#8217;,lat:15.4589,lon:75.0078},{name:&#8217;Hubballi&#8217;,lat:15.3647,lon:75.1240},  {name:&#8217;Davanagere&#8217;,lat:14.4644,lon:75.9218},{name:&#8217;Chitradurga&#8217;,lat:14.2296,lon:76.3981},  {name:&#8217;Tumakuru&#8217;,lat:13.3379,lon:77.1173},{name:&#8217;Bengaluru&#8217;,lat:12.9716,lon:77.5946},  {name:&#8217;Hosur&#8217;,lat:12.7409,lon:77.8253},{name:&#8217;Krishnagiri&#8217;,lat:12.5266,lon:78.2138},  {name:&#8217;Vellore&#8217;,lat:12.9165,lon:79.1325},{name:&#8217;Chennai&#8217;,lat:13.0827,lon:80.2707},  {name:&#8217;Nellore&#8217;,lat:14.4426,lon:79.9865},{name:&#8217;Ongole&#8217;,lat:15.5057,lon:80.0499},  {name:&#8217;Vijayawada&#8217;,lat:16.5062,lon:80.6480},{name:&#8217;Rajamahendravaram&#8217;,lat:17.0005,lon:81.8040},  {name:&#8217;Visakhapatnam&#8217;,lat:17.6868,lon:83.2185},{name:&#8217;Srikakulam&#8217;,lat:18.2949,lon:83.8938},  {name:&#8217;Berhampur&#8217;,lat:19.3150,lon:84.7941},{name:&#8217;Bhubaneswar&#8217;,lat:20.2961,lon:85.8245},  {name:&#8217;Cuttack&#8217;,lat:20.4625,lon:85.8830},{name:&#8217;Balasore&#8217;,lat:21.4927,lon:86.9316},  {name:&#8217;Kharagpur&#8217;,lat:22.3460,lon:87.2319},{name:&#8217;Kolkata&#8217;,lat:22.5726,lon:88.3639},  {name:&#8217;Durgapur&#8217;,lat:23.5204,lon:87.3119},{name:&#8217;Asansol&#8217;,lat:23.6739,lon:86.9524},  {name:&#8217;Dhanbad&#8217;,lat:23.7957,lon:86.4304},{name:&#8217;Hazaribagh&#8217;,lat:23.9925,lon:85.3637},  {name:&#8217;Gaya&#8217;,lat:24.7955,lon:85.0002},{name:&#8217;Sasaram&#8217;,lat:24.9474,lon:84.0317},  {name:&#8217;Prayagraj&#8217;,lat:25.4358,lon:81.8463},{name:&#8217;Kanpur&#8217;,lat:26.4499,lon:80.3319},  {name:&#8217;Agra&#8217;,lat:27.1767,lon:78.0081},{name:&#8217;Mathura&#8217;,lat:27.4924,lon:77.6737},  {name:&#8217;Faridabad&#8217;,lat:28.4082,lon:77.3178},{name:&#8217;Delhi&#8217;,lat:28.6139,lon:77.2090},];const GQ_MAP={};GQ_ROUTE.forEach(r=&gt;{GQ_MAP[r.name.toLowerCase()]=r;});\/* \u2500\u2500 India Background Cities (State Capitals + Major Cities) \u2500\u2500 *\/const INDIA_BG_CITIES = [  \/\/ State Capitals  {n:&#8217;Amaravati&#8217;,lat:16.5193,lon:80.5180,cap:true},  {n:&#8217;Itanagar&#8217;,lat:27.0844,lon:93.6053,cap:true},  {n:&#8217;Dispur&#8217;,lat:26.1433,lon:91.7898,cap:true},  {n:&#8217;Patna&#8217;,lat:25.5941,lon:85.1376,cap:true},  {n:&#8217;Raipur&#8217;,lat:21.2514,lon:81.6296,cap:true},  {n:&#8217;Panaji&#8217;,lat:15.4989,lon:73.8278,cap:true},  {n:&#8217;Gandhinagar&#8217;,lat:23.2156,lon:72.6369,cap:true},  {n:&#8217;Chandigarh&#8217;,lat:30.7333,lon:76.7794,cap:true},  {n:&#8217;Shimla&#8217;,lat:31.1048,lon:77.1734,cap:true},  {n:&#8217;Ranchi&#8217;,lat:23.3441,lon:85.3096,cap:true},  {n:&#8217;Bengaluru&#8217;,lat:12.9716,lon:77.5946,cap:true},  {n:&#8217;Thiruvananthapuram&#8217;,lat:8.5241,lon:76.9366,cap:true},  {n:&#8217;Bhopal&#8217;,lat:23.2599,lon:77.4126,cap:true},  {n:&#8217;Mumbai&#8217;,lat:19.0760,lon:72.8777,cap:true},  {n:&#8217;Imphal&#8217;,lat:24.8170,lon:93.9368,cap:true},  {n:&#8217;Shillong&#8217;,lat:25.5788,lon:91.8933,cap:true},  {n:&#8217;Aizawl&#8217;,lat:23.7307,lon:92.7173,cap:true},  {n:&#8217;Kohima&#8217;,lat:25.6751,lon:94.1086,cap:true},  {n:&#8217;Bhubaneswar&#8217;,lat:20.2961,lon:85.8245,cap:true},  {n:&#8217;Chandigarh&#8217;,lat:30.7333,lon:76.7794,cap:true},  {n:&#8217;Jaipur&#8217;,lat:26.9124,lon:75.7873,cap:true},  {n:&#8217;Gangtok&#8217;,lat:27.3314,lon:88.6138,cap:true},  {n:&#8217;Chennai&#8217;,lat:13.0827,lon:80.2707,cap:true},  {n:&#8217;Hyderabad&#8217;,lat:17.3850,lon:78.4867,cap:true},  {n:&#8217;Agartala&#8217;,lat:23.8315,lon:91.2868,cap:true},  {n:&#8217;Lucknow&#8217;,lat:26.8467,lon:80.9462,cap:true},  {n:&#8217;Dehradun&#8217;,lat:30.3165,lon:78.0322,cap:true},  {n:&#8217;Kolkata&#8217;,lat:22.5726,lon:88.3639,cap:true},  {n:&#8217;Delhi&#8217;,lat:28.6139,lon:77.2090,cap:true},  \/\/ Major cities  {n:&#8217;Srinagar&#8217;,lat:34.0837,lon:74.7973},  {n:&#8217;Jammu&#8217;,lat:32.7266,lon:74.8570},  {n:&#8217;Leh&#8217;,lat:34.1526,lon:77.5771},  {n:&#8217;Amritsar&#8217;,lat:31.6340,lon:74.8723},  {n:&#8217;Ludhiana&#8217;,lat:30.9010,lon:75.8573},  {n:&#8217;Jalandhar&#8217;,lat:31.3260,lon:75.5762},  {n:&#8217;Ambala&#8217;,lat:30.3782,lon:76.7767},  {n:&#8217;Hisar&#8217;,lat:29.1492,lon:75.7217},  {n:&#8217;Rohtak&#8217;,lat:28.8955,lon:76.6066},  {n:&#8217;Gurugram&#8217;,lat:28.4595,lon:77.0266},  {n:&#8217;Noida&#8217;,lat:28.5355,lon:77.3910},  {n:&#8217;Ghaziabad&#8217;,lat:28.6692,lon:77.4538},  {n:&#8217;Meerut&#8217;,lat:28.9845,lon:77.7064},  {n:&#8217;Aligarh&#8217;,lat:27.8974,lon:78.0880},  {n:&#8217;Agra&#8217;,lat:27.1767,lon:78.0081},  {n:&#8217;Mathura&#8217;,lat:27.4924,lon:77.6737},  {n:&#8217;Bareilly&#8217;,lat:28.3670,lon:79.4304},  {n:&#8217;Moradabad&#8217;,lat:28.8389,lon:78.7769},  {n:&#8217;Varanasi&#8217;,lat:25.3176,lon:82.9739},  {n:&#8217;Allahabad&#8217;,lat:25.4358,lon:81.8463},  {n:&#8217;Kanpur&#8217;,lat:26.4499,lon:80.3319},  {n:&#8217;Gorakhpur&#8217;,lat:26.7606,lon:83.3732},  {n:&#8217;Jhansi&#8217;,lat:25.4484,lon:78.5685},  {n:&#8217;Gwalior&#8217;,lat:26.2183,lon:78.1828},  {n:&#8217;Indore&#8217;,lat:22.7196,lon:75.8577},  {n:&#8217;Jabalpur&#8217;,lat:23.1815,lon:79.9864},  {n:&#8217;Ujjain&#8217;,lat:23.1793,lon:75.7849},  {n:&#8217;Surat&#8217;,lat:21.1702,lon:72.8311},  {n:&#8217;Ahmedabad&#8217;,lat:23.0225,lon:72.5714},  {n:&#8217;Vadodara&#8217;,lat:22.3072,lon:73.1812},  {n:&#8217;Rajkot&#8217;,lat:22.3039,lon:70.8022},  {n:&#8217;Bhavnagar&#8217;,lat:21.7645,lon:72.1519},  {n:&#8217;Jamnagar&#8217;,lat:22.4707,lon:70.0577},  {n:&#8217;Jodhpur&#8217;,lat:26.2389,lon:73.0243},  {n:&#8217;Udaipur&#8217;,lat:24.5854,lon:73.7125},  {n:&#8217;Kota&#8217;,lat:25.2138,lon:75.8648},  {n:&#8217;Ajmer&#8217;,lat:26.4499,lon:74.6399},  {n:&#8217;Bikaner&#8217;,lat:28.0229,lon:73.3119},  {n:&#8217;Pune&#8217;,lat:18.5204,lon:73.8567},  {n:&#8217;Nagpur&#8217;,lat:21.1458,lon:79.0882},  {n:&#8217;Nashik&#8217;,lat:19.9975,lon:73.7898},  {n:&#8217;Aurangabad&#8217;,lat:19.8762,lon:75.3433},  {n:&#8217;Solapur&#8217;,lat:17.6805,lon:75.9064},  {n:&#8217;Kolhapur&#8217;,lat:16.7050,lon:74.2433},  {n:&#8217;Amravati&#8217;,lat:20.9374,lon:77.7796},  {n:&#8217;Vizag&#8217;,lat:17.6868,lon:83.2185},  {n:&#8217;Vijayawada&#8217;,lat:16.5062,lon:80.6480},  {n:&#8217;Tirupati&#8217;,lat:13.6288,lon:79.4192},  {n:&#8217;Guntur&#8217;,lat:16.3067,lon:80.4365},  {n:&#8217;Warangal&#8217;,lat:17.9784,lon:79.5941},  {n:&#8217;Nellore&#8217;,lat:14.4426,lon:79.9865},  {n:&#8217;Coimbatore&#8217;,lat:11.0168,lon:76.9558},  {n:&#8217;Madurai&#8217;,lat:9.9252,lon:78.1198},  {n:&#8217;Tiruchirappalli&#8217;,lat:10.7905,lon:78.7047},  {n:&#8217;Salem&#8217;,lat:11.6643,lon:78.1460},  {n:&#8217;Tirunelveli&#8217;,lat:8.7139,lon:77.7567},  {n:&#8217;Kochi&#8217;,lat:9.9312,lon:76.2673},  {n:&#8217;Kozhikode&#8217;,lat:11.2588,lon:75.7804},  {n:&#8217;Thrissur&#8217;,lat:10.5276,lon:76.2144},  {n:&#8217;Kollam&#8217;,lat:8.8932,lon:76.6141},  {n:&#8217;Mysuru&#8217;,lat:12.2958,lon:76.6394},  {n:&#8217;Hubli&#8217;,lat:15.3647,lon:75.1240},  {n:&#8217;Mangaluru&#8217;,lat:12.9141,lon:74.8560},  {n:&#8217;Belagavi&#8217;,lat:15.8497,lon:74.4977},  {n:&#8217;Davangere&#8217;,lat:14.4644,lon:75.9218},  {n:&#8217;Guwahati&#8217;,lat:26.1445,lon:91.7362},  {n:&#8217;Silchar&#8217;,lat:24.8333,lon:92.7789},  {n:&#8217;Dibrugarh&#8217;,lat:27.4728,lon:94.9120},  {n:&#8217;Siliguri&#8217;,lat:26.7271,lon:88.3953},  {n:&#8217;Asansol&#8217;,lat:23.6739,lon:86.9524},  {n:&#8217;Durgapur&#8217;,lat:23.5204,lon:87.3119},  {n:&#8217;Howrah&#8217;,lat:22.5958,lon:88.2636},  {n:&#8217;Kharagpur&#8217;,lat:22.3460,lon:87.2319},  {n:&#8217;Dhanbad&#8217;,lat:23.7957,lon:86.4304},  {n:&#8217;Jamshedpur&#8217;,lat:22.8046,lon:86.2029},  {n:&#8217;Bokaro&#8217;,lat:23.6693,lon:86.1511},  {n:&#8217;Muzaffarpur&#8217;,lat:26.1209,lon:85.3647},  {n:&#8217;Gaya&#8217;,lat:24.7955,lon:85.0002},  {n:&#8217;Bhagalpur&#8217;,lat:25.2425,lon:86.9842},  {n:&#8217;Darbhanga&#8217;,lat:26.1542,lon:85.8918},  {n:&#8217;Bilaspur&#8217;,lat:22.0797,lon:82.1409},  {n:&#8217;Korba&#8217;,lat:22.3595,lon:82.7501},  {n:&#8217;Bhopal&#8217;,lat:23.2599,lon:77.4126},  {n:&#8217;Shivpuri&#8217;,lat:25.4231,lon:77.6577},  {n:&#8217;Rewa&#8217;,lat:24.5362,lon:81.3037},  {n:&#8217;Satna&#8217;,lat:24.5854,lon:80.8322},  {n:&#8217;Prayagraj&#8217;,lat:25.4358,lon:81.8463},  {n:&#8217;Puducherry&#8217;,lat:11.9416,lon:79.8083},  {n:&#8217;Vellore&#8217;,lat:12.9165,lon:79.1325},  {n:&#8217;Erode&#8217;,lat:11.3410,lon:77.7172},  {n:&#8217;Kakinada&#8217;,lat:16.9891,lon:82.2475},  {n:&#8217;Rajahmundry&#8217;,lat:17.0005,lon:81.8040},  {n:&#8217;Shillong&#8217;,lat:25.5788,lon:91.8933},  {n:&#8217;Imphal&#8217;,lat:24.8170,lon:93.9368},  {n:&#8217;Agartala&#8217;,lat:23.8315,lon:91.2868},  {n:&#8217;Aizawl&#8217;,lat:23.7307,lon:92.7173},  {n:&#8217;Dimapur&#8217;,lat:25.9010,lon:93.7360},  {n:&#8217;Udaipur&#8217;,lat:24.5854,lon:73.7125},  {n:&#8217;Alwar&#8217;,lat:27.5530,lon:76.6346},  {n:&#8217;Bharatpur&#8217;,lat:27.2152,lon:77.4938},  {n:&#8217;Pali&#8217;,lat:25.7711,lon:73.3234},  {n:&#8217;Haldwani&#8217;,lat:29.2183,lon:79.5130},  {n:&#8217;Roorkee&#8217;,lat:29.8543,lon:77.8880},  {n:&#8217;Haridwar&#8217;,lat:29.9457,lon:78.1642},  {n:&#8217;Rishikesh&#8217;,lat:30.0869,lon:78.2676},];let cities=[],cur=0,allYatraData=[];let inlineCal=null;let mainProjection=null, dashProjection=null;\/* \u2500\u2500 helper: append a city-name label to a D3 selection \u2500\u2500 *\/function appendCityLabel(sel, px, py, cityName, status, fromSheet) {  const isC = status===&#8217;current&#8217;;  const isV = status===&#8217;visited&#8217;;  const isSheet = !!fromSheet;  \/\/ For current city: animated pulsing label  if(isC){    const lbl = sel.append(&#8216;text&#8217;)      .attr(&#8216;x&#8217;, px)      .attr(&#8216;y&#8217;, py &#8211; 16)      .attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)      .attr(&#8216;font-size&#8217;, 11)      .attr(&#8216;font-weight&#8217;,&#8217;800&#8242;)      .attr(&#8216;font-family&#8217;,&#8221;&#8216;Outfit&#8217;,sans-serif&#8221;)      .attr(&#8216;fill&#8217;,&#8217;#e53935&#8242;)      .attr(&#8216;paint-order&#8217;,&#8217;stroke&#8217;)      .attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.98)&#8217;)      .attr(&#8216;stroke-width&#8217;, 3.5)      .attr(&#8216;stroke-linejoin&#8217;,&#8217;round&#8217;)      .attr(&#8216;pointer-events&#8217;,&#8217;none&#8217;)      .attr(&#8216;letter-spacing&#8217;,&#8217;0.5&#8242;)      .text(cityName);    \/\/ animate label opacity for live pulse effect    function animateLbl(){      lbl.transition().duration(800).attr(&#8216;opacity&#8217;,0.6)        .transition().duration(800).attr(&#8216;opacity&#8217;,1)        .on(&#8216;end&#8217;, animateLbl);    }    animateLbl();    return;  }  \/\/ Sheet-updated cities: orange, slightly bold  if(isSheet){    sel.append(&#8216;text&#8217;)      .attr(&#8216;x&#8217;, px)      .attr(&#8216;y&#8217;, py + 10)      .attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)      .attr(&#8216;font-size&#8217;, 6.5)      .attr(&#8216;font-weight&#8217;,&#8217;600&#8242;)      .attr(&#8216;font-family&#8217;,&#8221;&#8216;Outfit&#8217;,sans-serif&#8221;)      .attr(&#8216;fill&#8217;, isV ? &#8216;#cc6600&#8217; : &#8216;#ff8c00&#8217;)      .attr(&#8216;paint-order&#8217;,&#8217;stroke&#8217;)      .attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.95)&#8217;)      .attr(&#8216;stroke-width&#8217;, 2.5)      .attr(&#8216;stroke-linejoin&#8217;,&#8217;round&#8217;)      .attr(&#8216;pointer-events&#8217;,&#8217;none&#8217;)      .text(cityName);    return;  }  \/\/ GQ route cities (not sheet): small, subtle grey  sel.append(&#8216;text&#8217;)    .attr(&#8216;x&#8217;, px)    .attr(&#8216;y&#8217;, py + 9)    .attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)    .attr(&#8216;font-size&#8217;, 6.5)    .attr(&#8216;font-weight&#8217;,&#8217;400&#8242;)    .attr(&#8216;font-family&#8217;,&#8221;&#8216;Outfit&#8217;,sans-serif&#8221;)    .attr(&#8216;fill&#8217;, isV ? &#8216;rgba(26,74,46,0.6)&#8217; : &#8216;rgba(100,70,0,0.5)&#8217;)    .attr(&#8216;paint-order&#8217;,&#8217;stroke&#8217;)    .attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.85)&#8217;)    .attr(&#8216;stroke-width&#8217;, 2)    .attr(&#8216;stroke-linejoin&#8217;,&#8217;round&#8217;)    .attr(&#8216;pointer-events&#8217;,&#8217;none&#8217;)    .text(cityName);}\/* \u2500\u2500 Animated counter \u2500\u2500 *\/const _cs={};function fmtNum(v){if(v&gt;=10000)return(v\/1000).toFixed(1)+&#8217;K&#8217;;return String(Math.round(v));}function animateCounter(elId,targetNum,unit){  const el=document.getElementById(elId);if(!el)return;  const target=parseFloat(String(targetNum).replace(\/[^0-9.]\/g,&#8221;));  if(isNaN(target))return;  const prev=_cs[elId]||0;if(prev===target){el.textContent=fmtNum(target)+(unit||&#8221;);return;}  _cs[elId]=target;const dur=600,t0=performance.now();  el.classList.remove(&#8216;pop-anim&#8217;);void el.offsetWidth;el.classList.add(&#8216;pop-anim&#8217;);  setTimeout(()=&gt;el.classList.remove(&#8216;pop-anim&#8217;),450);  function step(now){const t=Math.min((now-t0)\/dur,1),e=1-Math.pow(1-t,3),v=prev+(target-prev)*e;el.textContent=fmtNum(v)+(unit||&#8221;);if(t&lt;1)requestAnimationFrame(step);}  requestAnimationFrame(step);}function setCircle(id,pct){  const el=document.getElementById(id);if(!el)return;  const r=27,c=2*Math.PI*r,offset=c-(pct\/100)*c;  el.style.strokeDasharray=c;el.style.strokeDashoffset=offset;}function toISO(d){return`${d.getFullYear()}-${String(d.getMonth()+1).padStart(2,&#8217;0&#8242;)}-${String(d.getDate()).padStart(2,&#8217;0&#8242;)}`;}function todayISO(){return toISO(new Date());}function parseISO(s){if(!s)return null;const d=new Date(s);return isNaN(d)?null:d;}function formatDate(iso){const d=parseISO(iso);return d?d.toLocaleDateString(&#8216;en-IN&#8217;,{day:&#8217;numeric&#8217;,month:&#8217;short&#8217;}):iso;}function dNorm(v){  if(!v)return null;  if(typeof v===&#8217;string&#8217;&amp;&amp;\/^d{4}-d{2}-d{2}$\/.test(v))return v;  try{const d=new Date(v);if(!isNaN(d.getTime()))return`${d.getFullYear()}-${String(d.getMonth()+1).padStart(2,&#8217;0&#8242;)}-${String(d.getDate()).padStart(2,&#8217;0&#8242;)}`;}catch(e){}  return null;}function dFmt(s){const n=dNorm(s);return n?new Date(n).toLocaleDateString(&#8216;en-US&#8217;,{year:&#8217;numeric&#8217;,month:&#8217;long&#8217;,day:&#8217;numeric&#8217;}):s;}function getCurrentIndex(list){  const t=todayISO();if(!list.length)return 0;  if(t&lt;list[0].iso)return 0;if(t&gt;=list[list.length-1].iso)return list.length-1;  let idx=0;for(let i=0;i&lt;list.length;i++){if(list[i].iso&lt;=t)idx=i;}return idx;}function buildCitiesFromSheet(data){  if(!data||!data.length)return null;  const seen={},list=[];  data.forEach(item=&gt;{    const iso=dNorm(item.Date);if(!iso)return;if(seen[iso])return;    const rawCity=(item.City||&#8221;).trim();if(!rawCity)return;    const isBreak=rawCity.toLowerCase()===&#8217;break&#8217;||(item[&#8216;Status&#8217;]||&#8221;).toLowerCase()===&#8217;break&#8217;||(item[&#8216;Type&#8217;]||&#8221;).toLowerCase()===&#8217;break&#8217;;    let lat=parseFloat(item.Latitude),lon=parseFloat(item.Longitude);    if(isNaN(lat)||isNaN(lon)){      if(isBreak){const p=list[list.length-1];if(!p)return;lat=p.lat;lon=p.lon;}      else{const gq=GQ_MAP[rawCity.toLowerCase()];if(!gq)return;lat=gq.lat;lon=gq.lon;}    }    seen[iso]=true;    list.push({name:isBreak?&#8217;Break&#8217;:rawCity,lat,lon,iso,dateStr:formatDate(iso),isBreak,_fromSheet:true});  });  if(!list.length)return null;  list.sort((a,b)=&gt;a.iso.localeCompare(b.iso));  const s=parseISO(list[0].iso);  list.forEach((c,i)=&gt;{const d=parseISO(c.iso);c.day=s&amp;&amp;d?Math.round((d-s)\/86400000)+1:i+1;c.idx=i;});  return list;}function buildCitiesFromGQ(){  const S=new Date(&#8216;2026-05-13&#8217;),T=100,step=T\/(GQ_ROUTE.length-1);  return GQ_ROUTE.map((c,i)=&gt;{    const dn=Math.round(i*step)+1,d=new Date(S);d.setDate(d.getDate()+dn-1);    const iso=toISO(d);return{&#8230;c,day:dn,iso,dateStr:formatDate(iso),idx:i};  });}const INDIA_GEOJSON_URL = &#8216;https:\/\/cdn.jsdelivr.net\/gh\/udit-001\/india-maps-data@ef25ebc\/geojson\/india.geojson&#8217;;let indiaGeoJSON = null;async function loadIndiaGeoJSON() {  if (indiaGeoJSON) return indiaGeoJSON;  try {    const res = await fetch(INDIA_GEOJSON_URL);    const data = await res.json();    indiaGeoJSON = data;    return indiaGeoJSON;  } catch(e) {    console.warn(&#8216;Primary GeoJSON failed, trying fallback:&#8217;, e);    try {      const fallbackRes = await fetch(&#8216;https:\/\/raw.githubusercontent.com\/datasets\/geo-countries\/master\/data\/countries.geojson&#8217;);      const fallbackData = await fallbackRes.json();      indiaGeoJSON = {        type: &#8216;FeatureCollection&#8217;,        features: fallbackData.features.filter(f =&gt;          (f.properties.ADMIN === &#8216;India&#8217; || f.properties.ISO_A3 === &#8216;IND&#8217;)        )      };      return indiaGeoJSON;    } catch(fbErr) {      console.error(&#8216;All GeoJSON sources failed:&#8217;, fbErr);      return null;    }  }}function makeProjection(svgEl) {  const rect = svgEl.getBoundingClientRect();  const W = rect.width || svgEl.parentElement.clientWidth || 500;  const H = rect.height || svgEl.parentElement.clientHeight || 500;  const proj = d3.geoMercator().center([82.5, 22]).scale(1).translate([W\/2, H\/2]);  const topLeft = proj([68.0, 37.5]);  const bottomRight = proj([97.5, 6.5]);  const kX = (W * 0.92) \/ (bottomRight[0] &#8211; topLeft[0]);  const kY = (H * 0.92) \/ (bottomRight[1] &#8211; topLeft[1]);  const k = Math.min(kX, kY);  proj.scale(k);  const c = proj([82.5, 22]);  proj.translate([W\/2 + (W\/2 &#8211; c[0]), H\/2 + (H\/2 &#8211; c[1])]);  return proj;}function latLonToXY(proj, lat, lon) {  const pt = proj([lon, lat]);  return pt ? {x: pt[0], y: pt[1]} : null;}\/* \u2500\u2500 renderD3Map \u2014 used by dashboard map \u2500\u2500 *\/function renderD3Map(svgId, tooltipId, citiesList, currentIdx, extraPoints) {  const svgEl = document.getElementById(svgId);  if (!svgEl) return;  const svg = d3.select(&#8216;#&#8217;+svgId);  svg.selectAll(&#8216;*&#8217;).remove();  const rect = svgEl.getBoundingClientRect();  const W = rect.width || svgEl.parentElement.clientWidth || 500;  const H = rect.height || svgEl.parentElement.clientHeight || 500;  svg.attr(&#8216;viewBox&#8217;, `0 0 ${W} ${H}`);  const proj = makeProjection(svgEl);  if (svgId === &#8216;main-map-svg&#8217;) mainProjection = proj;  else dashProjection = proj;  const pathGen = d3.geoPath().projection(proj);  const tooltip = document.getElementById(tooltipId);  svg.append(&#8216;rect&#8217;).attr(&#8216;width&#8217;,W).attr(&#8216;height&#8217;,H).attr(&#8216;fill&#8217;,&#8217;#b8d4e8&#8242;);  if (indiaGeoJSON &amp;&amp; indiaGeoJSON.features &amp;&amp; indiaGeoJSON.features.length) {    svg.selectAll(&#8216;.india-path&#8217;)      .data(indiaGeoJSON.features)      .enter().append(&#8216;path&#8217;)      .attr(&#8216;class&#8217;,&#8217;india-path&#8217;)      .attr(&#8216;d&#8217;, pathGen)      .attr(&#8216;fill&#8217;,&#8217;#d4ebd4&#8242;)      .attr(&#8216;stroke&#8217;,&#8217;#5a9a6a&#8217;)      .attr(&#8216;stroke-width&#8217;, 1.0);  } else {    svg.append(&#8216;rect&#8217;).attr(&#8216;x&#8217;,W*0.05).attr(&#8216;y&#8217;,H*0.05).attr(&#8216;width&#8217;,W*0.9).attr(&#8216;height&#8217;,H*0.9)      .attr(&#8216;rx&#8217;,8).attr(&#8216;fill&#8217;,&#8217;#d4ebd4&#8242;).attr(&#8216;stroke&#8217;,&#8217;#5a9a6a&#8217;).attr(&#8216;stroke-width&#8217;,1.5);    svg.append(&#8216;text&#8217;).attr(&#8216;x&#8217;,W\/2).attr(&#8216;y&#8217;,H\/2).attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)      .attr(&#8216;fill&#8217;,&#8217;#5a9a6a&#8217;).attr(&#8216;font-size&#8217;,13).attr(&#8216;font-family&#8217;,&#8217;Outfit,sans-serif&#8217;)      .text(&#8216;India Map Loading&#8230;&#8217;);  }  function cityPt(c){ return latLonToXY(proj, c.lat, c.lon); }  const donePts = [];  for(let i=0; i&lt;=currentIdx; i++){    const p = cityPt(citiesList[i]);    if(p &amp;&amp; (donePts.length===0 || donePts[donePts.length-1][0]!==p.x || donePts[donePts.length-1][1]!==p.y))      donePts.push([p.x, p.y]);  }  if(donePts.length&gt;1){    svg.append(&#8216;polyline&#8217;)      .attr(&#8216;points&#8217;, donePts.map(p=&gt;p.join(&#8216;,&#8217;)).join(&#8216; &#8216;))      .attr(&#8216;fill&#8217;,&#8217;none&#8217;).attr(&#8216;stroke&#8217;,&#8217;#2d7a4a&#8217;).attr(&#8216;stroke-width&#8217;,2.8)      .attr(&#8216;stroke-linejoin&#8217;,&#8217;round&#8217;).attr(&#8216;stroke-linecap&#8217;,&#8217;round&#8217;).attr(&#8216;opacity&#8217;,0.95);  }  const upPts = [];  for(let i=currentIdx; i&lt;citiesList.length; i++){    const p = cityPt(citiesList[i]);    if(p &amp;&amp; (upPts.length===0 || upPts[upPts.length-1][0]!==p.x || upPts[upPts.length-1][1]!==p.y))      upPts.push([p.x, p.y]);  }  if(upPts.length&gt;1){    svg.append(&#8216;polyline&#8217;)      .attr(&#8216;points&#8217;, upPts.map(p=&gt;p.join(&#8216;,&#8217;)).join(&#8216; &#8216;))      .attr(&#8216;fill&#8217;,&#8217;none&#8217;).attr(&#8216;stroke&#8217;,&#8217;rgba(255,160,60,0.55)&#8217;).attr(&#8216;stroke-width&#8217;,2)      .attr(&#8216;stroke-dasharray&#8217;,&#8217;7 5&#8242;).attr(&#8216;stroke-linecap&#8217;,&#8217;round&#8217;).attr(&#8216;opacity&#8217;,0.9);  }  citiesList.forEach((c,i)=&gt;{    const p = cityPt(c);    if(!p) return;    const st = i&lt;currentIdx?&#8217;visited&#8217;:i===currentIdx?&#8217;current&#8217;:&#8217;upcoming&#8217;;    const g = svg.append(&#8216;g&#8217;).attr(&#8216;class&#8217;,&#8217;city-marker&#8217;).attr(&#8216;cursor&#8217;,&#8217;default&#8217;);    if(st===&#8217;current&#8217;){      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,11).attr(&#8216;fill&#8217;,&#8217;rgba(255,102,0,0.20)&#8217;).attr(&#8216;stroke&#8217;,&#8217;none&#8217;);      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,7).attr(&#8216;fill&#8217;,&#8217;#ff6600&#8242;).attr(&#8216;stroke&#8217;,&#8217;#fff&#8217;).attr(&#8216;stroke-width&#8217;,2);    } else if(st===&#8217;visited&#8217;){      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,4).attr(&#8216;fill&#8217;,&#8217;#2d7a4a&#8217;).attr(&#8216;stroke&#8217;,&#8217;#4CAF7D&#8217;).attr(&#8216;stroke-width&#8217;,1.5);    } else {      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,3.5).attr(&#8216;fill&#8217;,&#8217;#ff9933&#8242;).attr(&#8216;stroke&#8217;,&#8217;#fff&#8217;).attr(&#8216;stroke-width&#8217;,1);    }    \/* \u2500\u2500 city name label \u2500\u2500 *\/    appendCityLabel(g, p.x, p.y, c.name, st, c._fromSheet||false);    g.on(&#8216;mouseenter&#8217;, (evt)=&gt;{      tooltip.innerHTML=`&lt;strong&gt;${c.name}&lt;\/strong&gt;&lt;br&gt;${c.dateStr}, 2026 \u00b7 Day ${c.day}`;      tooltip.style.opacity=&#8217;1&#8242;;    }).on(&#8216;mousemove&#8217;,(evt)=&gt;{      const wrap = svgEl.parentElement.getBoundingClientRect();      let tx = evt.clientX &#8211; wrap.left + 12;      let ty = evt.clientY &#8211; wrap.top &#8211; 10;      if(tx + 180 &gt; wrap.width) tx = tx &#8211; 190;      tooltip.style.left=tx+&#8217;px&#8217;;tooltip.style.top=ty+&#8217;px&#8217;;    }).on(&#8216;mouseleave&#8217;,()=&gt;{ tooltip.style.opacity=&#8217;0&#8242;; });  });  if(extraPoints){    extraPoints.forEach(ep=&gt;{      const p = latLonToXY(proj, ep.lat, ep.lon);      if(!p) return;      svg.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,5)        .attr(&#8216;fill&#8217;,ep.color||&#8217;#e07030&#8242;).attr(&#8216;stroke&#8217;,&#8217;#fff&#8217;).attr(&#8216;stroke-width&#8217;,1.5).attr(&#8216;opacity&#8217;,0.85);    });  }  if(svgId===&#8217;main-map-svg&#8217; &amp;&amp; citiesList[currentIdx]){    document.getElementById(&#8216;map-badge-city&#8217;).textContent = citiesList[currentIdx].name;  }}\/* \u2500\u2500 renderMainMapWithZoom \u2014 main live map with D3 zoom \u2500\u2500 *\/let zoomBehavior = null;function renderMainMapWithZoom(){  const svgEl = document.getElementById(&#8216;main-map-svg&#8217;);  if(!svgEl) return;  const svg = d3.select(&#8216;#main-map-svg&#8217;);  svg.selectAll(&#8216;*&#8217;).remove();  const rect = svgEl.getBoundingClientRect();  const W = rect.width || svgEl.parentElement.clientWidth || 500;  const H = rect.height || svgEl.parentElement.clientHeight || 500;  svg.attr(&#8216;viewBox&#8217;,`0 0 ${W} ${H}`);  const proj = makeProjection(svgEl);  mainProjection = proj;  const pathGen = d3.geoPath().projection(proj);  const tooltip = document.getElementById(&#8216;map-tooltip&#8217;);  const root = svg.append(&#8216;g&#8217;).attr(&#8216;id&#8217;,&#8217;zoom-root&#8217;);  root.append(&#8216;rect&#8217;).attr(&#8216;width&#8217;,W).attr(&#8216;height&#8217;,H).attr(&#8216;fill&#8217;,&#8217;#b8d4e8&#8242;);  if (indiaGeoJSON &amp;&amp; indiaGeoJSON.features &amp;&amp; indiaGeoJSON.features.length) {    root.selectAll(&#8216;.india-path&#8217;)      .data(indiaGeoJSON.features)      .enter().append(&#8216;path&#8217;)      .attr(&#8216;class&#8217;,&#8217;india-path&#8217;)      .attr(&#8216;d&#8217;,pathGen)      .attr(&#8216;fill&#8217;,&#8217;#d4ebd4&#8242;)      .attr(&#8216;stroke&#8217;,&#8217;#5a9a6a&#8217;)      .attr(&#8216;stroke-width&#8217;, 1.0);  }  \/* \u2500\u2500 Background India cities layer \u2500\u2500 *\/  const yataCityNames = new Set(cities.map(c=&gt;c.name.toLowerCase()));  INDIA_BG_CITIES.forEach(bc=&gt;{    if(yataCityNames.has(bc.n.toLowerCase())) return; \/\/ skip if already on yatra route    const pt = proj([bc.lon, bc.lat]);    if(!pt) return;    const bx=pt[0], by=pt[1];    const bg = root.append(&#8216;g&#8217;).attr(&#8216;pointer-events&#8217;,&#8217;none&#8217;);    \/\/ dot    bg.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,bx).attr(&#8216;cy&#8217;,by)      .attr(&#8216;r&#8217;, bc.cap ? 2 : 1.5)      .attr(&#8216;fill&#8217;, bc.cap ? &#8216;#aaa&#8217; : &#8216;#bbb&#8217;)      .attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.6)&#8217;)      .attr(&#8216;stroke-width&#8217;, 0.7);    \/\/ label    bg.append(&#8216;text&#8217;)      .attr(&#8216;x&#8217;, bx).attr(&#8216;y&#8217;, by &#8211; 3)      .attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)      .attr(&#8216;font-size&#8217;, bc.cap ? 5.5 : 5)      .attr(&#8216;font-weight&#8217;, bc.cap ? &#8216;500&#8217; : &#8216;400&#8217;)      .attr(&#8216;font-family&#8217;,&#8221;&#8216;Outfit&#8217;,sans-serif&#8221;)      .attr(&#8216;fill&#8217;, bc.cap ? &#8216;rgba(80,80,80,0.75)&#8217; : &#8216;rgba(110,110,110,0.6)&#8217;)      .attr(&#8216;paint-order&#8217;,&#8217;stroke&#8217;)      .attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.8)&#8217;)      .attr(&#8216;stroke-width&#8217;, 1.8)      .attr(&#8216;stroke-linejoin&#8217;,&#8217;round&#8217;)      .text(bc.n);  });  function cityPt(c){ const pt=proj([c.lon,c.lat]); return pt?{x:pt[0],y:pt[1]}:null; }  const donePts=[];  for(let i=0;i&lt;=cur;i++){    const p=cityPt(cities[i]);    if(p&amp;&amp;(donePts.length===0||donePts[donePts.length-1][0]!==p.x||donePts[donePts.length-1][1]!==p.y))      donePts.push([p.x,p.y]);  }  if(donePts.length&gt;1){    const doneLineEl = root.append(&#8216;polyline&#8217;)      .attr(&#8216;points&#8217;,donePts.map(p=&gt;p.join(&#8216;,&#8217;)).join(&#8216; &#8216;))      .attr(&#8216;fill&#8217;,&#8217;none&#8217;).attr(&#8216;stroke&#8217;,&#8217;#1db954&#8242;).attr(&#8216;stroke-width&#8217;,4)      .attr(&#8216;stroke-linejoin&#8217;,&#8217;round&#8217;).attr(&#8216;stroke-linecap&#8217;,&#8217;round&#8217;).attr(&#8216;opacity&#8217;,1);    let totalLen = 0;    for(let i=1;i&lt;donePts.length;i++){      const dx=donePts[i][0]-donePts[i-1][0], dy=donePts[i][1]-donePts[i-1][1];      totalLen += Math.sqrt(dx*dx+dy*dy);    }    doneLineEl.attr(&#8216;stroke-dasharray&#8217;, totalLen+&#8217; &#8216;+totalLen)      .attr(&#8216;stroke-dashoffset&#8217;, totalLen);    doneLineEl.transition().duration(1800).ease(d3.easeCubicInOut)      .attr(&#8216;stroke-dashoffset&#8217;, 0);  }  const upPts=[];  for(let i=cur;i&lt;cities.length;i++){    const p=cityPt(cities[i]);    if(p&amp;&amp;(upPts.length===0||upPts[upPts.length-1][0]!==p.x||upPts[upPts.length-1][1]!==p.y))      upPts.push([p.x,p.y]);  }  if(upPts.length&gt;1)    root.append(&#8216;polyline&#8217;).attr(&#8216;points&#8217;,upPts.map(p=&gt;p.join(&#8216;,&#8217;)).join(&#8216; &#8216;))      .attr(&#8216;fill&#8217;,&#8217;none&#8217;).attr(&#8216;stroke&#8217;,&#8217;#ff8c00&#8242;).attr(&#8216;stroke-width&#8217;,2.5)      .attr(&#8216;stroke-dasharray&#8217;,&#8217;8 5&#8242;).attr(&#8216;stroke-linecap&#8217;,&#8217;round&#8217;).attr(&#8216;opacity&#8217;,0.85);  cities.forEach((c,i)=&gt;{    const p=cityPt(c); if(!p) return;    const st=i&lt;cur?&#8217;visited&#8217;:i===cur?&#8217;current&#8217;:&#8217;upcoming&#8217;;    const fromSheet = c._fromSheet || false;    const g=root.append(&#8216;g&#8217;).attr(&#8216;cursor&#8217;,&#8217;default&#8217;);    if(st===&#8217;current&#8217;){      const outerRing = g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,14)        .attr(&#8216;fill&#8217;,&#8217;rgba(229,57,53,0.18)&#8217;).attr(&#8216;stroke&#8217;,&#8217;rgba(229,57,53,0.4)&#8217;).attr(&#8216;stroke-width&#8217;,1.5);      function pulseRing(){        outerRing.transition().duration(900).attr(&#8216;r&#8217;,18).attr(&#8216;opacity&#8217;,0.1)          .transition().duration(900).attr(&#8216;r&#8217;,14).attr(&#8216;opacity&#8217;,1)          .on(&#8216;end&#8217;,pulseRing);      }      pulseRing();      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,7)        .attr(&#8216;fill&#8217;,&#8217;#e53935&#8242;).attr(&#8216;stroke&#8217;,&#8217;#fff&#8217;).attr(&#8216;stroke-width&#8217;,2.2);      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,2.5).attr(&#8216;fill&#8217;,&#8217;#fff&#8217;);    } else if(st===&#8217;visited&#8217;){      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,3.8).attr(&#8216;fill&#8217;,&#8217;#27ae60&#8242;).attr(&#8216;stroke&#8217;,&#8217;#4CAF7D&#8217;).attr(&#8216;stroke-width&#8217;,1.5);    } else {      g.append(&#8216;circle&#8217;).attr(&#8216;cx&#8217;,p.x).attr(&#8216;cy&#8217;,p.y).attr(&#8216;r&#8217;,3).attr(&#8216;fill&#8217;,&#8217;#ff9933&#8242;).attr(&#8216;stroke&#8217;,&#8217;#fff&#8217;).attr(&#8216;stroke-width&#8217;,1);    }    \/* \u2500\u2500 city name label on main live map \u2500\u2500 *\/    appendCityLabel(g, p.x, p.y, c.name, st, fromSheet);    g.append(&#8216;rect&#8217;).attr(&#8216;x&#8217;,p.x-12).attr(&#8216;y&#8217;,p.y-12).attr(&#8216;width&#8217;,24).attr(&#8216;height&#8217;,24).attr(&#8216;fill&#8217;,&#8217;transparent&#8217;)      .on(&#8216;mouseenter&#8217;,(evt)=&gt;{        tooltip.innerHTML=`&lt;strong&gt;${c.name}&lt;\/strong&gt;&lt;br&gt;${c.dateStr}, 2026 \u00b7 Day ${c.day}`;        tooltip.style.opacity=&#8217;1&#8242;;      })      .on(&#8216;mousemove&#8217;,(evt)=&gt;{        const wrap=svgEl.parentElement.getBoundingClientRect();        let tx=evt.clientX-wrap.left+12, ty=evt.clientY-wrap.top-10;        if(tx+180&gt;wrap.width) tx=tx-190;        tooltip.style.left=tx+&#8217;px&#8217;; tooltip.style.top=ty+&#8217;px&#8217;;      })      .on(&#8216;mouseleave&#8217;,()=&gt;tooltip.style.opacity=&#8217;0&#8242;)      .on(&#8216;click&#8217;,()=&gt;{        if(!zoomBehavior) return;        const s=3.2;        d3.select(&#8216;#main-map-svg&#8217;).transition().duration(600).call(          zoomBehavior.transform,          d3.zoomIdentity.translate(W\/2,H\/2).scale(s).translate(-p.x,-p.y)        );      });  });  const cc=cities[cur];  if(cc){    document.getElementById(&#8216;map-badge-city&#8217;).textContent=cc.name;  }  if(!zoomBehavior){    zoomBehavior=d3.zoom().scaleExtent([0.7, 10]).on(&#8216;zoom&#8217;,(evt)=&gt;{      root.attr(&#8216;transform&#8217;,evt.transform);    });  } else {    zoomBehavior.on(&#8216;zoom&#8217;,(evt)=&gt;root.attr(&#8216;transform&#8217;,evt.transform));  }  svg.call(zoomBehavior);  svg.append(&#8216;rect&#8217;).attr(&#8216;x&#8217;,W-46).attr(&#8216;y&#8217;,10).attr(&#8216;width&#8217;,36).attr(&#8216;height&#8217;,70).attr(&#8216;rx&#8217;,8)    .attr(&#8216;fill&#8217;,&#8217;rgba(10,40,20,0.75)&#8217;).attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.2)&#8217;).attr(&#8216;stroke-width&#8217;,1);  svg.append(&#8216;text&#8217;).attr(&#8216;x&#8217;,W-28).attr(&#8216;y&#8217;,34).attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)    .attr(&#8216;fill&#8217;,&#8217;#fff&#8217;).attr(&#8216;font-size&#8217;,18).attr(&#8216;font-family&#8217;,&#8217;sans-serif&#8217;).attr(&#8216;cursor&#8217;,&#8217;pointer&#8217;)    .text(&#8216;+&#8217;).on(&#8216;click&#8217;,()=&gt;svg.transition().duration(300).call(zoomBehavior.scaleBy,1.5));  svg.append(&#8216;line&#8217;).attr(&#8216;x1&#8217;,W-44).attr(&#8216;x2&#8217;,W-12).attr(&#8216;y1&#8217;,45).attr(&#8216;y2&#8217;,45)    .attr(&#8216;stroke&#8217;,&#8217;rgba(255,255,255,0.25)&#8217;).attr(&#8216;stroke-width&#8217;,1);  svg.append(&#8216;text&#8217;).attr(&#8216;x&#8217;,W-28).attr(&#8216;y&#8217;,63).attr(&#8216;text-anchor&#8217;,&#8217;middle&#8217;)    .attr(&#8216;fill&#8217;,&#8217;#fff&#8217;).attr(&#8216;font-size&#8217;,18).attr(&#8216;font-family&#8217;,&#8217;sans-serif&#8217;).attr(&#8216;cursor&#8217;,&#8217;pointer&#8217;)    .text(&#8216;\u2212&#8217;).on(&#8216;click&#8217;,()=&gt;svg.transition().duration(300).call(zoomBehavior.scaleBy,0.67));}function renderDashMap(data){  const svgEl=document.getElementById(&#8216;d-map-svg&#8217;);if(!svgEl)return;  const today=todayISO();  const pts=[];  data.forEach(item=&gt;{    const iso=dNorm(item.Date);if(!iso)return;    const cn=(item.City||&#8221;).trim();if(!cn)return;    let la=parseFloat(item.Latitude),lo=parseFloat(item.Longitude);    if(isNaN(la)||isNaN(lo)){const gq=GQ_MAP[cn.toLowerCase()];if(!gq)return;la=gq.lat;lo=gq.lon;}    let color=iso&lt;today?&#8217;#aaa&#8217;:iso===today?&#8217;#e53935&#8242;:&#8217;#e07030&#8242;;    pts.push({lat:la,lon:lo,name:cn,iso,color,current:iso===today});  });  renderD3Map(&#8216;d-map-svg&#8217;,&#8217;d-map-tooltip&#8217;,cities,cur,pts);}function haversineKm(a,b){  const R=6371,dLat=(b.lat-a.lat)*Math.PI\/180,dLon=(b.lon-a.lon)*Math.PI\/180;  const s=Math.sin(dLat\/2)**2+Math.cos(a.lat*Math.PI\/180)*Math.cos(b.lat*Math.PI\/180)*Math.sin(dLon\/2)**2;  return R*2*Math.atan2(Math.sqrt(s),Math.sqrt(1-s));}function updateSidebar(){  if(!cities.length)return;  const c=cities[cur],nxt=cur&lt;cities.length-1?cities[cur+1]:null;  const pct=Math.round((cur\/(cities.length-1))*100);  const daysDone=Math.max(0,c.day-1);  const daysLeft=Math.max(0,100-c.day+1);  \/\/ NAYA lagao:let kmDone = 0;if (allYatraData &amp;&amp; allYatraData.length) {  const today = todayISO();  allYatraData.forEach(item =&gt; {    const iso = dNorm(item.Date);    if (!iso || iso &gt; today) return;    const km = parseFloat(String(item.KM || item.km || item[&#8216;KM Covered&#8217;] || 0).replace(\/,\/g, &#8221;));    if (!isNaN(km)) kmDone += km;  });} else {  \/\/ Fallback: haversine  for (let i = 0; i &lt; cur; i++)    kmDone += haversineKm(cities[i], cities[i+1]);}kmDone = Math.round(kmDone);  let peopleMet=0;  const today=todayISO();  if(allYatraData&amp;&amp;allYatraData.length){    allYatraData.forEach(item=&gt;{      const iso=dNorm(item.Date);if(!iso||iso&gt;today)return;      const keys=Object.keys(item);const pk=keys.find(k=&gt;\/people\/i.test(k));      if(pk){const n=parseInt(String(item[pk]||&#8217;0&#8242;).replace(\/,\/g,&#8221;),10);if(!isNaN(n))peopleMet+=n;}    });  }  if(peopleMet===0&amp;&amp;window.statsData&amp;&amp;window.statsData.totalPeople) peopleMet=window.statsData.totalPeople;  document.getElementById(&#8216;hdr-day&#8217;).textContent=`Day ${c.day} of 100`;  document.getElementById(&#8216;sb-city&#8217;).textContent=c.isBreak?`${c.name} \u2014 Rest Day`:c.name;  document.getElementById(&#8216;sb-date&#8217;).textContent=`${c.dateStr}, 2026 \u00b7 Day ${c.day}`;  document.getElementById(&#8216;day-pill&#8217;).textContent=`Day ${c.day}`;  const badge=document.getElementById(&#8216;live-badge&#8217;);  if(c.isBreak){badge.classList.add(&#8216;on-break&#8217;);document.getElementById(&#8216;live-txt&#8217;).textContent=&#8217;BREAK&#8217;;}  else{badge.classList.remove(&#8216;on-break&#8217;);document.getElementById(&#8216;live-txt&#8217;).textContent=&#8217;LIVE&#8217;;}  if(nxt){document.getElementById(&#8216;sb-next&#8217;).textContent=nxt.name;document.getElementById(&#8216;sb-next-when&#8217;).textContent=nxt.dateStr+&#8217;, 2026&#8242;;}  else{document.getElementById(&#8216;sb-next&#8217;).textContent=&#8217;Yatra Sampurna&#8217;;document.getElementById(&#8216;sb-next-when&#8217;).textContent=&#8217;\u2726 100 Days Complete \u2726&#8217;;}  document.getElementById(&#8216;prog-fill&#8217;).style.width=Math.max(1,pct)+&#8217;%&#8217;;  document.getElementById(&#8216;prog-txt&#8217;).textContent=pct+&#8217;% complete&#8217;;  animateCounter(&#8216;stat-done2&#8217;,daysDone);animateCounter(&#8216;stat-left2&#8217;,daysLeft);  animateCounter(&#8216;stat-people2&#8217;,peopleMet);animateCounter(&#8216;stat-km2&#8242;,kmDone,&#8217; km&#8217;);  setCircle(&#8216;circ-done2&#8217;,Math.round((daysDone\/100)*100));setCircle(&#8216;circ-left2&#8217;,Math.round((daysLeft\/100)*100));}function buildList(){  const list=document.getElementById(&#8216;rlist&#8217;);list.innerHTML=&#8221;;  cities.forEach((c,i)=&gt;{    const st=i&lt;cur?&#8217;visited&#8217;:i===cur?&#8217;current&#8217;:&#8217;upcoming&#8217;;    const item=document.createElement(&#8216;div&#8217;);item.className=&#8217;ritem&#8217;;    item.onclick=()=&gt;{      if(mainProjection &amp;&amp; zoomBehavior){        const pt=mainProjection([c.lon,c.lat]);        if(pt){          const svgEl=document.getElementById(&#8216;main-map-svg&#8217;);          const W=svgEl.getBoundingClientRect().width;          const H=svgEl.getBoundingClientRect().height;          d3.select(&#8216;#main-map-svg&#8217;).transition().duration(600).call(            zoomBehavior.transform,            d3.zoomIdentity.translate(W\/2,H\/2).scale(3.2).translate(-pt[0],-pt[1])          );        }      }    };    const dw=document.createElement(&#8216;div&#8217;);dw.className=&#8217;rdot-wrap&#8217;;    const dot=document.createElement(&#8216;div&#8217;);dot.className=&#8217;rdot &#8216;+(c.isBreak&amp;&amp;st===&#8217;current&#8217;?&#8217;break&#8217;:st);    dw.appendChild(dot);    if(i&lt;cities.length-1){const ln=document.createElement(&#8216;div&#8217;);ln.className=&#8217;rconnect&#8217;;dw.appendChild(ln);}    const nm=document.createElement(&#8216;div&#8217;);nm.className=&#8217;rname &#8216;+st;nm.textContent=c.name;    if(st===&#8217;current&#8217;&amp;&amp;c.isBreak){const t=document.createElement(&#8216;span&#8217;);t.className=&#8217;tag-break&#8217;;t.textContent=&#8217;BREAK&#8217;;nm.appendChild(t);}    else if(st===&#8217;current&#8217;){const t=document.createElement(&#8216;span&#8217;);t.className=&#8217;tag-live&#8217;;t.textContent=&#8217;LIVE&#8217;;nm.appendChild(t);}    if(st===&#8217;upcoming&#8217;&amp;&amp;i===cur+1){const t=document.createElement(&#8216;span&#8217;);t.className=&#8217;tag-next&#8217;;t.textContent=&#8217;NEXT&#8217;;nm.appendChild(t);}    const info=document.createElement(&#8216;div&#8217;);info.style.flex=&#8217;1&#8242;;info.style.overflow=&#8217;hidden&#8217;;info.appendChild(nm);    const dt=document.createElement(&#8216;div&#8217;);dt.className=&#8217;rdate&#8217;;dt.textContent=c.dateStr;    item.appendChild(dw);item.appendChild(info);item.appendChild(dt);list.appendChild(item);  });  const items=list.querySelectorAll(&#8216;.ritem&#8217;);  if(items[cur])setTimeout(()=&gt;{const el=items[cur];const container=el.closest(&#8216;.rlist&#8217;);if(container){container.scrollTop=el.offsetTop-container.offsetTop-40;}},200);}function showCalEvtPopup(dateStr){  const nd=dNorm(dateStr);  const body=document.getElementById(&#8216;cal-evt-body&#8217;);  const title=document.getElementById(&#8216;cal-evt-title&#8217;);  const ev=allYatraData.find(item=&gt;dNorm(item.Date)===nd);  if(ev){    title.textContent=ev[&#8216;Event Name&#8217;]||ev.City||&#8217;Event Details&#8217;;    body.innerHTML=`      &lt;div&gt;&lt;span&gt;City&lt;\/span&gt;&lt;div&gt;${ev.City||&#8217;N\/A&#8217;}&lt;\/div&gt;&lt;\/div&gt;      &lt;div&gt;&lt;span&gt;Date&lt;\/span&gt;&lt;div&gt;${dFmt(ev.Date)}&lt;\/div&gt;&lt;\/div&gt;      ${ev[&#8216;Event Name&#8217;]?`&lt;div&gt;&lt;span&gt;Event&lt;\/span&gt;&lt;div&gt;${ev[&#8216;Event Name&#8217;]}&lt;\/div&gt;&lt;\/div&gt;`:&#8221;}      ${ev.Host?`&lt;div&gt;&lt;span&gt;Hosted By&lt;\/span&gt;&lt;div&gt;${ev.Host}&lt;\/div&gt;&lt;\/div&gt;`:&#8221;}      ${ev.Venue?`&lt;div&gt;&lt;span&gt;Venue&lt;\/span&gt;&lt;div&gt;${ev.Venue}&lt;\/div&gt;&lt;\/div&gt;`:&#8221;}      ${(ev.Time!==undefined&amp;&amp;ev.Time!==null&amp;&amp;ev.Time!==&#8221;)?`&lt;div&gt;&lt;span&gt;Time&lt;\/span&gt;&lt;div&gt;${fmtTime(ev.Time)}&lt;\/div&gt;&lt;\/div&gt;`:&#8221;}      ${ev[&#8216;Short Description&#8217;]?`&lt;div&gt;&lt;span&gt;Description&lt;\/span&gt;&lt;div&gt;${ev[&#8216;Short Description&#8217;]}&lt;\/div&gt;&lt;\/div&gt;`:&#8221;}    `;  } else {    const dateObj=parseISO(nd),start=parseISO(&#8216;2026-05-13&#8217;),end=parseISO(&#8216;2026-08-20&#8242;);    title.textContent=nd?dFmt(nd):&#8217;No Event&#8217;;    if(dateObj&amp;&amp;start&amp;&amp;end&amp;&amp;dateObj&gt;=start&amp;&amp;dateObj&lt;=end){      const city=cities.find(c=&gt;c.iso===nd);      body.innerHTML=city        ?`&lt;div&gt;&lt;span&gt;Location&lt;\/span&gt;&lt;div&gt;${city.name}&lt;\/div&gt;&lt;\/div&gt;&lt;div&gt;&lt;span&gt;Day&lt;\/span&gt;&lt;div&gt;Day ${city.day} of 100&lt;\/div&gt;&lt;\/div&gt;&lt;div style=&#8221;padding-top:8px&#8221;&gt;No specific event scheduled&lt;\/div&gt;`        :`&lt;div&gt;No event scheduled for this date&lt;\/div&gt;`;    } else {      body.innerHTML=`&lt;div&gt;No Yatra event on this date&lt;\/div&gt;`;    }  }  document.getElementById(&#8216;cal-evt-overlay&#8217;).classList.add(&#8216;show&#8217;);  \/\/ expand iframe to full viewport so fixed overlay covers everything  document.documentElement.style.height=&#8217;100vh&#8217;;  document.body.style.height=&#8217;100vh&#8217;;  document.body.style.overflow=&#8217;hidden&#8217;;  try{    var iframes=window.top.document.querySelectorAll(&#8216;iframe&#8217;);    iframes.forEach(function(f){      if(f.contentWindow===window){        f._origHeight=f._origHeight||f.style.height;        f._origPos=f._origPos||f.style.position;        f.style.cssText=&#8217;height:&#8217;+window.top.innerHeight+&#8217;px !important;position:fixed !important;top:0 !important;left:0 !important;width:100% !important;z-index:99999 !important;margin:0 !important;&#8217;;      }    });  }catch(e){}}function closeCalEvt(){  document.getElementById(&#8216;cal-evt-overlay&#8217;).classList.remove(&#8216;show&#8217;);  document.documentElement.style.height=&#8221;;  document.body.style.height=&#8221;;  document.body.style.overflow=&#8221;;  try{    var iframes=window.top.document.querySelectorAll(&#8216;iframe&#8217;);    iframes.forEach(function(f){      if(f.contentWindow===window){        f.style.cssText=&#8221;;        if(f._origHeight) f.style.height=f._origHeight;      }    });  }catch(e){}}document.addEventListener(&#8216;keydown&#8217;,e=&gt;{  if(e.key===&#8217;Escape&#8217;){closeCalEvt();closeDash();document.getElementById(&#8216;india-lb&#8217;).style.display=&#8217;none&#8217;;}});\/* \u2500\u2500 Shared calendar event builder \u2014 used by both calendars \u2500\u2500 *\/function buildCalEvents(data){  const today=todayISO();  const evts=[];  data.forEach(item=&gt;{    const iso=dNorm(item.Date);if(!iso)return;    const city=(item.City||&#8221;).trim();if(!city||city.toLowerCase()===&#8217;break&#8217;)return;    const eventName=(item[&#8216;Event Name&#8217;]||&#8221;).trim();    const label=eventName?`${city} \u2013 ${eventName}`:city;    let color=iso&lt;today?&#8217;#888&#8242;:iso===today?&#8217;#e53935&#8242;:&#8217;#e07030&#8242;;    evts.push({title:label,start:iso,color,allDay:true,      extendedProps:{dateStr:iso}});  });  return evts;}function initInlineCal(){  const el=document.getElementById(&#8216;inline-calendar&#8217;);  inlineCal=new FullCalendar.Calendar(el,{    initialView:&#8217;dayGridMonth&#8217;,    headerToolbar:{left:&#8217;prev,next today&#8217;,center:&#8217;title&#8217;,right:&#8221;},    height:&#8217;auto&#8217;,    themeSystem:&#8217;standard&#8217;,    eventDisplay:&#8217;block&#8217;,    eventMaxStack:3,    dayMaxEvents:3,    eventDidMount:function(info){      info.el.style.fontSize=&#8217;9px&#8217;;      info.el.style.padding=&#8217;1px 3px&#8217;;      info.el.style.borderRadius=&#8217;3px&#8217;;      info.el.style.cursor=&#8217;pointer&#8217;;    },    dateClick:info=&gt;showCalEvtPopup(info.dateStr),    eventClick:info=&gt;{      const ds=info.event.extendedProps.dateStr||info.event.startStr||(info.event.start?info.event.start.toISOString().split(&#8216;T&#8217;)[0]:&#8221;);      if(ds) showCalEvtPopup(ds);    }  });  inlineCal.render();}function updateInlineCal(data){  if(!inlineCal)return;  inlineCal.removeAllEvents();  inlineCal.addEventSource(buildCalEvents(data));}function fmtTime(v){  if(v===undefined||v===null||v===&#8221;)return&#8217;\u2014&#8217;;  const s=String(v).trim();  if(s===&#8221;||s===&#8217;0&#8217;||s.toLowerCase()===&#8217;false&#8217;||s===&#8217;\u2014&#8217;)return&#8217;\u2014&#8217;;  \/\/ 1899-12-30 = Google Sheets empty time cell (Excel zero date)  if(s.startsWith(&#8216;1899&#8217;)||s.startsWith(&#8216;1900-01-0&#8242;))return&#8217;\u2014&#8217;;  \/\/ Apps Script sends Date as &#8220;yyyy-MM-dd&#8221; \u2014 if it&#8217;s a full date with no time, skip  \/\/ But if Apps Script sends time as &#8220;1899-12-30 HH:mm:ss&#8221; extract time part  const spaceMatch=s.match(\/d{4}-d{2}-d{2}s+(d{1,2}):(d{2})\/);  if(spaceMatch){    const h=parseInt(spaceMatch[1],10),m=parseInt(spaceMatch[2],10);    if(h===0&amp;&amp;m===0)return&#8217;\u2014&#8217;;    const ampm=h&gt;=12?&#8217;PM&#8217;:&#8217;AM&#8217;,hh=h%12===0?12:h%12;    return hh+&#8217;:&#8217;+String(m).padStart(2,&#8217;0&#8242;)+&#8217; &#8216;+ampm;  }  \/\/ Decimal fraction: Google Sheets internal time (0.375 = 9:00 AM)  const num=parseFloat(s);  if(!isNaN(num)&amp;&amp;num&gt;0&amp;&amp;num&lt;1){    const totalMin=Math.round(num*1440);    const h=Math.floor(totalMin\/60),m=totalMin%60;    const ampm=h&gt;=12?&#8217;PM&#8217;:&#8217;AM&#8217;,hh=h%12===0?12:h%12;    return hh+&#8217;:&#8217;+String(m).padStart(2,&#8217;0&#8242;)+&#8217; &#8216;+ampm;  }  \/\/ ISO datetime with T (e.g. &#8220;1899-12-30T09:00:00.000Z&#8221;)  if(s.includes(&#8216;T&#8217;)){    const tp=s.split(&#8216;T&#8217;)[1];    if(tp){      const tm=tp.match(\/^(d{1,2}):(d{2})\/);      if(tm){        const h=parseInt(tm[1],10),m=parseInt(tm[2],10);        if(h===0&amp;&amp;m===0)return&#8217;\u2014&#8217;;        const ampm=h&gt;=12?&#8217;PM&#8217;:&#8217;AM&#8217;,hh=h%12===0?12:h%12;        return hh+&#8217;:&#8217;+String(m).padStart(2,&#8217;0&#8242;)+&#8217; &#8216;+ampm;      }    }    return&#8217;\u2014&#8217;;  }  \/\/ Plain HH:MM or HH:MM:SS with optional AM\/PM  const match=s.match(\/^(d{1,2}):(d{2})(?::d{2})?(s*(AM|PM))?$\/i);  if(match){    let h=parseInt(match[1],10);const m=parseInt(match[2],10);    const period=(match[4]||&#8221;).toUpperCase();    if(h===0&amp;&amp;m===0&amp;&amp;!period)return&#8217;\u2014&#8217;;    if(period===&#8217;PM&#8217;&amp;&amp;h!==12)h+=12;    else if(period===&#8217;AM&#8217;&amp;&amp;h===12)h=0;    const ampm=h&gt;=12?&#8217;PM&#8217;:&#8217;AM&#8217;,hh=h%12===0?12:h%12;    return hh+&#8217;:&#8217;+String(m).padStart(2,&#8217;0&#8242;)+&#8217; &#8216;+ampm;  }  \/\/ Already readable like &#8220;10:00 AM&#8221;  if(\/d.*[AaPp][Mm]\/.test(s))return s;  return&#8217;\u2014&#8217;;}function render(){  renderMainMapWithZoom();  updateSidebar();  buildList();}const REFRESH=5;let dCalendar=null,dashInited=false;function expandIframe(){  document.documentElement.style.height=&#8217;100vh&#8217;;  document.body.style.height=&#8217;100vh&#8217;;  document.body.style.overflow=&#8217;hidden&#8217;;  try{    var iframes=window.top.document.querySelectorAll(&#8216;iframe&#8217;);    iframes.forEach(function(f){      if(f.contentWindow===window){        f._origHeight=f._origHeight||f.style.height;        f._origPos=f._origPos||f.style.position;        f.style.cssText=&#8217;height:&#8217;+window.top.innerHeight+&#8217;px !important;position:fixed !important;top:0 !important;left:0 !important;width:100% !important;z-index:99999 !important;margin:0 !important;&#8217;;      }    });  }catch(e){}}function restoreIframe(){  document.documentElement.style.height=&#8221;;  document.body.style.height=&#8221;;  document.body.style.overflow=&#8221;;  try{    var iframes=window.top.document.querySelectorAll(&#8216;iframe&#8217;);    iframes.forEach(function(f){      if(f.contentWindow===window){        f.style.cssText=&#8221;;        if(f._origHeight) f.style.height=f._origHeight;      }    });  }catch(e){}}function showCalendar(){  document.getElementById(&#8216;dash-overlay&#8217;).classList.add(&#8216;show&#8217;);  expandIframe();  if(!dashInited){dashInited=true;setTimeout(initDash,80);}  else renderDashMap(allYatraData);}function closeDash(){document.getElementById(&#8216;dash-overlay&#8217;).classList.remove(&#8216;show&#8217;);closeDEvt();restoreIframe();}function closeDEvt(){document.getElementById(&#8216;d-evt-modal&#8217;).classList.remove(&#8216;show&#8217;);}function initDash(){  renderDashMap(allYatraData);  const calEl=document.getElementById(&#8216;d-calendar&#8217;);  dCalendar=new FullCalendar.Calendar(calEl,{    initialView:&#8217;dayGridMonth&#8217;,    headerToolbar:{left:&#8217;prev,next today&#8217;,center:&#8217;title&#8217;,right:&#8217;dayGridMonth&#8217;},    height:&#8217;auto&#8217;,    contentHeight:&#8217;auto&#8217;,    themeSystem:&#8217;standard&#8217;,    eventDisplay:&#8217;block&#8217;,    eventMaxStack:3,    dayMaxEvents:3,    eventDidMount:function(info){      info.el.style.fontSize=&#8217;9px&#8217;;      info.el.style.padding=&#8217;1px 3px&#8217;;      info.el.style.borderRadius=&#8217;3px&#8217;;      info.el.style.cursor=&#8217;pointer&#8217;;    },    dateClick:info=&gt;showCalEvtPopup(info.dateStr),    eventClick:info=&gt;{      const ds=info.event.extendedProps.dateStr||info.event.startStr||(info.event.start?info.event.start.toISOString().split(&#8216;T&#8217;)[0]:&#8221;);      if(ds) showCalEvtPopup(ds);    }  });  dCalendar.render();  updateDashUI(allYatraData);  setInterval(fetchDashData,REFRESH*60*1000);}async function fetchDashData(){  try{    const res=await fetch(`${API_URL}?t=${Date.now()}`);    const result=await res.json();    if(result.status===&#8217;success&#8217;){      allYatraData=result.data;      \/\/ Debug: log first item&#8217;s Time field to console      if(result.data&amp;&amp;result.data[0]) console.log(&#8216;[TIME DEBUG]&#8217;,JSON.stringify(result.data[0]));      if(typeof result.totalPeople===&#8217;number&#8217;&amp;&amp;result.totalPeople&gt;0){        window.statsData={totalPeople:result.totalPeople,rows:result.stats||[]};      } else if(result.stats&amp;&amp;Array.isArray(result.stats)){        const total=result.stats.reduce((sum,row)=&gt;{          const keys=Object.keys(row);const pk=keys.find(k=&gt;\/peoples*met|peoplemet|people_met|count\/i.test(k));          const n=pk?parseInt(String(row[pk]||&#8217;0&#8242;).replace(\/,\/g,&#8221;),10):0;return sum+(isNaN(n)?0:n);        },0);        window.statsData={totalPeople:total,rows:result.stats};      }      const sc=buildCitiesFromSheet(allYatraData);      if(sc&amp;&amp;sc.length){cities=sc;cur=getCurrentIndex(cities);render();}      else render();      updateInlineCal(allYatraData);      if(dashInited)updateDashUI(allYatraData);    }  }catch(e){console.warn(&#8216;Sheet fetch failed, using GQ fallback:&#8217;,e);}}function updateDashUI(data){  if(!dCalendar)return;  const today=todayISO();  dCalendar.removeAllEvents();  dCalendar.addEventSource(buildCalEvents(data));  \/\/ Update current city banner  const ce=data.find(item=&gt;dNorm(item.Date)===today);  const banner=document.getElementById(&#8216;d-current-city-text&#8217;);  if(ce){banner.textContent=`${ce.City||&#8221;} (${ce[&#8216;Event Name&#8217;]||&#8221;})`;banner.style.color=&#8217;#e53935&#8242;;}  else{banner.textContent=&#8217;No event scheduled for today.&#8217;;banner.style.color=&#8221;;}  renderDashMap(data);}let resizeTimer;function onResize(){  clearTimeout(resizeTimer);  resizeTimer=setTimeout(()=&gt;{    if(cities.length) renderMainMapWithZoom();    if(dashInited) renderDashMap(allYatraData);  },250);}window.addEventListener(&#8216;resize&#8217;, onResize);window.addEventListener(&#8216;orientationchange&#8217;, onResize);if(window.visualViewport){  window.visualViewport.addEventListener(&#8216;resize&#8217;, onResize);}async function init(){  cities=buildCitiesFromGQ();cur=getCurrentIndex(cities);  initInlineCal();  await loadIndiaGeoJSON();  render();  await fetchDashData();}init();\/\/ This is a new code jQuery(document).ready(function($) {    setTimeout(function() {        if ($(&#8216;#tcb_landing_page&#8217;).length) {            $(&#8216;html, body&#8217;).animate({                scrollTop: $(&#8216;#tcb_landing_page&#8217;).offset().top            }, 800);        }    }, 1000); \/\/ 2000ms = 1 seconds});jQuery(function($) {    $(&#8216;#yatra-invite&#8217;).click(function(e) {        e.preventDefault();        var target = $(&#8216;#take-action-invite-yatra-now&#8217;);        if (target.length) {            $(&#8216;html, body&#8217;).stop().animate({                scrollTop: target.offset().top            }, 800);        }    });});0[\/tcb-script]<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Energy Swaraj Yatra Bharat Climate Satyagraha Yatra 100 Days Sacred Journey Across Bharat \u2014 Golden Quadrilateral May 13 \u2013 Aug 20, 2026 Day \u2014 of 100 Today&#8217;s Schedule Invite Yatra Journey Stats 0 Days Done 100 Days Left KMs Covered 0 People Met 0 LIVE Day \u2014 Loading\u2026 \u2014 Next Stop \u2014 \u2014 Yatra Progress [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"parent":0,"menu_order":0,"comment_status":"closed","ping_status":"closed","template":"","meta":{"footnotes":"","tve_updated_post":"<div class=\"thrv_wrapper thrv_custom_html_shortcode\" style=\"\" data-css=\"tve-u-69e5dd6367aff1\"><meta charset=\"UTF-8\">\n<meta name=\"viewport\" content=\"width=device-width,initial-scale=1,minimum-scale=1,viewport-fit=cover\">\n<title>Energy Swaraj Yatra<\/title>\n<link href=\"https:\/\/fonts.googleapis.com\/css2?family=Cormorant+Garamond:ital,wght@0,400;0,600;0,700;1,400&amp;family=Outfit:wght@300;400;500;600;700&amp;display=swap\" rel=\"stylesheet\">\n<link href=\"https:\/\/cdn.jsdelivr.net\/npm\/fullcalendar@5.11.3\/main.min.css\" rel=\"stylesheet\">\n<style>\nhtml { scroll-behavior: auto !important; }\n:root {\n  --green-deep: #1a4a2e;\n  --green-mid: #2d7a4a;\n  --green-light: #4CAF7D;\n  --green-pale: #e8f5ee;\n  --amber: #d47c0f;\n  --amber-light: #f5c842;\n  --cream: #faf8f2;\n  --text-dark: #1a1a1a;\n  --text-mid: #4a4a4a;\n  --text-light: #888;\n  --red-live: #e53935;\n  --shadow-sm: 0 2px 12px rgba(26,74,46,0.10);\n  --shadow-md: 0 4px 24px rgba(26,74,46,0.13);\n  --radius-sm: 10px;\n  --radius-md: 15px;\n}\n*{box-sizing:border-box;margin:0;padding:0;}\nbody{background:var(--cream);font-family:'Outfit',sans-serif;color:var(--text-dark);overflow-x:hidden;min-height:100vh;}\n.hdr{background:linear-gradient(135deg,var(--green-deep) 0%,#0d3320 40%,#1e5c35 70%,var(--green-mid) 100%);padding:0 28px;height:68px;display:flex;align-items:center;justify-content:space-between;position:sticky;top:0;z-index:200;box-shadow:0 2px 20px rgba(0,0,0,0.25);}\n.hdr::before{content:'';position:absolute;inset:0;background:repeating-linear-gradient(90deg,transparent 0,transparent 60px,rgba(255,255,255,0.025) 60px,rgba(255,255,255,0.025) 61px);pointer-events:none;}\n.hdr-left{display:flex;align-items:center;gap:14px;}\n.hdr-emblem{width:50px;height:34px;border-radius:4px;overflow:hidden;display:flex;align-items:center;justify-content:center;box-shadow:0 0 0 2px rgba(245,200,66,0.3),0 0 14px rgba(212,124,15,0.35);flex-shrink:0;}\n.hdr-title{font-family:'Cormorant Garamond',serif;font-size:14px;font-weight:700;color:#fff;letter-spacing:1px;text-transform:uppercase;line-height:1;white-space:nowrap;}\n.hdr-sub{font-size:10px;color:rgba(255,255,255,0.55);letter-spacing:1px;margin-top:2px;}\n.hdr-right{display:flex;align-items:center;gap:8px;flex-shrink:0;}\n.hdr-dates-badge{display:flex;align-items:center;gap:6px;background:rgba(255,255,255,0.1);border:1px solid rgba(255,255,255,0.2);border-radius:20px;padding:4px 10px;}\n.hdr-dates-txt{font-size:10px;color:rgba(255,255,255,0.85);letter-spacing:0.3px;white-space:nowrap;}\n.hdr-day-badge{background:linear-gradient(135deg,var(--amber),var(--amber-light));border-radius:20px;padding:4px 10px;font-weight:700;font-size:11px;color:#1a1a1a;box-shadow:0 2px 8px rgba(212,124,15,0.4);white-space:nowrap;}\n.btn-schedule{display:flex;align-items:center;gap:5px;background:rgba(255,255,255,0.15);border:1px solid rgba(255,255,255,0.35);color:#fff;border-radius:20px;padding:5px 12px;font-size:11px;font-weight:500;cursor:pointer;transition:all .2s;white-space:nowrap;}\n.btn-schedule:hover{background:rgba(255,255,255,0.25);}\n.btn-invite{display:flex;align-items:center;gap:5px;background:linear-gradient(135deg,var(--amber),var(--amber-light));border:none;color:#1a1a1a;border-radius:20px;padding:5px 12px;font-size:11px;font-weight:700;cursor:pointer;transition:all .2s;text-decoration:none;box-shadow:0 2px 8px rgba(212,124,15,0.35);white-space:nowrap;}\n.btn-invite:hover{transform:translateY(-1px);box-shadow:0 4px 14px rgba(212,124,15,0.5);}\n.btn-invite-popup{display:block;width:100%;text-align:center;background:linear-gradient(135deg,var(--amber),var(--amber-light));color:#1a1a1a;font-weight:700;font-size:13px;padding:12px 20px;border-radius:8px;text-decoration:none;margin-top:16px;box-shadow:0 2px 10px rgba(212,124,15,0.3);transition:all .2s;}\n.btn-invite-popup:hover{transform:translateY(-1px);box-shadow:0 4px 16px rgba(212,124,15,0.5);}\n.main-layout{display:grid;grid-template-columns:280px 1fr 320px;grid-template-rows:calc(100dvh - 68px);gap:0;overflow:hidden;}\n.left-panel{background:var(--green-deep);display:flex;flex-direction:column;overflow-y:auto;border-right:1px solid rgba(26,74,46,0.15);}\n.left-img-wrap{position:relative;flex-shrink:0;height:310px;overflow:hidden;}\n.left-img-wrap img{width:100%;height:100%;object-fit:cover;display:block;}\n.left-img-overlay{position:absolute;inset:0;background:linear-gradient(to bottom,transparent 40%,rgba(10,40,20,0.85) 100%);}\n.left-img-caption{position:absolute;bottom:14px;left:16px;right:16px;font-family:'Cormorant Garamond',serif;font-size:17px;font-weight:600;color:#fff;letter-spacing:1px;}\n.left-img-caption span{display:block;font-size:11px;font-weight:400;font-family:'Outfit',sans-serif;color:rgba(255,255,255,0.65);letter-spacing:2px;text-transform:uppercase;margin-bottom:3px;}\n.left-info{padding:18px 16px;flex:1;display:flex;flex-direction:column;gap:14px;}\n.live-card{background:rgba(229,57,53,0.12);border:1px solid rgba(229,57,53,0.3);border-radius:var(--radius-sm);padding:14px;}\n.live-top{display:flex;align-items:center;justify-content:space-between;margin-bottom:8px;}\n.live-badge{display:flex;align-items:center;gap:6px;background:rgba(229,57,53,0.15);border:1px solid rgba(229,57,53,0.4);border-radius:20px;padding:3px 10px;font-size:10px;font-weight:700;color:var(--red-live);letter-spacing:1.5px;}\n.live-badge.on-break{background:rgba(33,150,243,0.12);border-color:rgba(33,150,243,0.35);color:#1565c0;}\n.ldot{width:6px;height:6px;border-radius:50%;background:var(--red-live);animation:pulse-dot 1.2s ease-in-out infinite;}\n@keyframes pulse-dot{0%,100%{opacity:1;box-shadow:0 0 0 0 rgba(229,57,53,0.5);}50%{opacity:.7;box-shadow:0 0 0 5px rgba(229,57,53,0);}}\n@keyframes pulse-orange{0%,100%{box-shadow:0 0 0 0 rgba(180,60,0,0.7);}50%{box-shadow:0 0 0 8px rgba(180,60,0,0);}}\n.day-pill{background:rgba(255,255,255,0.1);border-radius:12px;padding:2px 10px;font-size:11px;color:rgba(255,255,255,0.6);font-weight:500;}\n.live-city{font-family:'Cormorant Garamond',serif;font-size:26px;font-weight:700;color:#fff;letter-spacing:2px;line-height:1;}\n.live-date{font-size:12px;color:rgba(255,255,255,0.5);margin-top:4px;}\n.next-card{background:rgba(255,255,255,0.07);border:1px solid rgba(255,255,255,0.12);border-radius:var(--radius-sm);padding:12px 14px;}\n.next-lbl{font-size:9px;font-weight:600;letter-spacing:2px;color:rgba(255,255,255,0.4);text-transform:uppercase;margin-bottom:6px;}\n.next-city{font-family:'Cormorant Garamond',serif;font-size:18px;font-weight:600;color:var(--amber-light);}\n.next-when{font-size:11px;color:rgba(255,255,255,0.45);margin-top:3px;}\n.progress-wrap{background:rgba(255,255,255,0.07);border-radius:var(--radius-sm);padding:14px;}\n.progress-lbl{font-size:9px;font-weight:600;letter-spacing:2px;color:rgba(255,255,255,0.4);text-transform:uppercase;margin-bottom:10px;}\n.prog-bar-bg{height:6px;background:rgba(255,255,255,0.1);border-radius:4px;overflow:hidden;}\n.prog-bar-fill{height:100%;background:linear-gradient(90deg,var(--green-mid),var(--green-light),var(--amber-light));border-radius:4px;transition:width .6s ease;}\n.prog-txt{font-size:11px;color:rgba(255,255,255,0.4);margin-top:6px;text-align:right;}\n.route-section{flex:1;overflow:hidden;display:flex;flex-direction:column;}\n.route-lbl{font-size:9px;font-weight:600;letter-spacing:2px;color:rgba(255,255,255,0.4);text-transform:uppercase;margin-bottom:8px;}\n.rlist{flex:1;overflow-y:auto;display:flex;flex-direction:column;max-height:220px;}\n.rlist::-webkit-scrollbar{width:3px;}.rlist::-webkit-scrollbar-track{background:transparent;}.rlist::-webkit-scrollbar-thumb{background:rgba(255,255,255,0.15);border-radius:2px;}\n.ritem{display:flex;align-items:center;gap:8px;padding:5px 4px;border-radius:6px;cursor:pointer;transition:background .15s;}\n.ritem:hover{background:rgba(255,255,255,0.07);}\n.rdot-wrap{display:flex;flex-direction:column;align-items:center;flex-shrink:0;}\n.rdot{width:8px;height:8px;border-radius:50%;flex-shrink:0;border:1.5px solid rgba(255,255,255,0.2);background:rgba(255,255,255,0.1);}\n.rdot.visited{background:rgba(255,255,255,0.3);border-color:rgba(255,255,255,0.4);}\n.rdot.current{background:var(--red-live);border-color:#ff6b6b;box-shadow:0 0 8px rgba(229,57,53,0.6);animation:pulse-dot 1.2s infinite;}\n.rdot.upcoming{background:transparent;border-color:rgba(255,255,255,0.15);}\n.rdot.break{background:#1565c0;border-color:#42a5f5;}\n.rconnect{width:1.5px;height:5px;background:rgba(255,255,255,0.1);margin-top:1px;}\n.rname{font-size:12px;color:rgba(255,255,255,0.65);flex:1;}\n.rname.current{color:#fff;font-weight:600;}.rname.visited{color:rgba(255,255,255,0.35);}\n.rdate{font-size:10px;color:rgba(255,255,255,0.25);white-space:nowrap;margin-left:auto;}\n.tag-live{font-size:8px;background:rgba(229,57,53,0.2);border:1px solid rgba(229,57,53,0.4);color:var(--red-live);border-radius:3px;padding:1px 4px;margin-left:4px;}\n.tag-next{font-size:8px;background:rgba(212,124,15,0.2);border:1px solid rgba(212,124,15,0.35);color:var(--amber-light);border-radius:3px;padding:1px 4px;margin-left:4px;}\n.tag-break{font-size:8px;background:rgba(33,150,243,0.15);border:1px solid rgba(33,150,243,0.3);color:#90caf9;border-radius:3px;padding:1px 4px;margin-left:4px;}\n.map-panel{position:relative;overflow:hidden;background:#c8dfc8;}\n#main-map-svg-wrap{width:100%;height:100%;position:relative;}\n#main-map-svg-wrap svg{width:100%;height:100%;display:block;}\n.map-overlay-badge{position:absolute;bottom:18px;left:50%;transform:translateX(-50%);z-index:10;background:rgba(10,40,20,0.85);backdrop-filter:blur(8px);border:1px solid rgba(255,140,0,0.4);border-radius:30px;padding:7px 20px;display:flex;align-items:center;gap:10px;box-shadow:0 4px 20px rgba(0,0,0,0.2);pointer-events:none;white-space:nowrap;}\n.map-badge-txt{font-size:12px;color:rgba(255,255,255,0.85);font-weight:500;}\n.map-badge-city{font-family:'Cormorant Garamond',serif;font-size:15px;font-weight:700;color:#ff9933;letter-spacing:1px;}\n#map-tooltip{position:absolute;background:rgba(10,30,18,0.95);border:1px solid rgba(255,140,0,0.35);border-radius:8px;color:#fff;font-family:'Outfit',sans-serif;font-size:12px;padding:7px 11px;pointer-events:none;opacity:0;transition:opacity .15s;z-index:20;max-width:180px;}\n#map-tooltip strong{color:#ff9933;font-family:'Cormorant Garamond',serif;font-size:15px;display:block;margin-bottom:2px;}\n.right-panel{background:var(--cream);border-left:1px solid rgba(26,74,46,0.1);display:flex;flex-direction:column;overflow-y:auto;}\n.right-panel::-webkit-scrollbar{width:4px;}.right-panel::-webkit-scrollbar-track{background:var(--cream);}.right-panel::-webkit-scrollbar-thumb{background:rgba(26,74,46,0.15);border-radius:2px;}\n.rp-section{padding:16px;border-bottom:1px solid rgba(26,74,46,0.08);}\n.rp-lbl{font-size:9px;font-weight:700;letter-spacing:2.5px;color:rgba(26,74,46,0.5);text-transform:uppercase;margin-bottom:12px;display:flex;align-items:center;gap:6px;}\n.rp-lbl::after{content:'';flex:1;height:1px;background:rgba(26,74,46,0.1);}\n.circ-bg{fill:none;stroke:rgba(26,74,46,0.08);stroke-width:5;}\n.circ-fg{fill:none;stroke:var(--green-mid);stroke-width:5;stroke-linecap:round;transition:stroke-dashoffset .8s cubic-bezier(.4,0,.2,1);}\n.circ-fg.amber{stroke:var(--amber);}\n.cal-wrap{border-radius:var(--radius-sm);overflow:hidden;background:#fff;box-shadow:var(--shadow-sm);}\n\n\/* \u2500\u2500 Shared FullCalendar base styling (applies to both calendars) \u2500\u2500 *\/\n.fc .fc-button {\n  background: var(--green-deep) !important;\n  border: 1px solid rgba(255,255,255,0.2) !important;\n  color: #fff !important;\n  padding: 3px 9px !important;\n  font-size: 11px !important;\n  border-radius: 5px !important;\n  box-shadow: none !important;\n  text-transform: none !important;\n  font-weight: 500 !important;\n  line-height: 1.4 !important;\n}\n.fc .fc-button:hover { background: var(--green-mid) !important; }\n.fc .fc-button-primary:not(:disabled):active,\n.fc .fc-button-primary:not(:disabled).fc-button-active {\n  background: var(--green-mid) !important;\n  border-color: rgba(255,255,255,0.3) !important;\n}\n.fc .fc-toolbar { gap: 6px; flex-wrap: wrap; padding: 8px 10px; margin: 0 !important; }\n.fc .fc-toolbar-title { font-size: 13px !important; font-weight: 600; }\n.fc .fc-toolbar.fc-header-toolbar { background: var(--green-deep); border-radius: 0; }\n.fc th { background: rgba(26,74,46,0.05); }\n.fc .fc-col-header-cell-cushion { font-size: 10px; color: var(--green-deep); font-weight: 600; padding: 4px; text-decoration: none !important; }\n.fc .fc-daygrid-day-number { font-size: 11px; color: var(--text-mid); padding: 3px; text-decoration: none !important; }\n.fc .fc-day-today { background: rgba(77,175,125,0.08) !important; }\n.fc .fc-daygrid-event { font-size: 9px; border-radius: 3px; }\n.fc .fc-toolbar-title { color: #fff !important; }\n\n\/* \u2500\u2500 Inline calendar specific overrides \u2500\u2500 *\/\n#inline-calendar { font-size: 11px; }\n#inline-calendar .fc-toolbar { background: var(--green-deep); }\n\n\/* \u2500\u2500 Dashboard calendar specific overrides \u2500\u2500 *\/\n#d-calendar { font-size: 11px; }\n#d-calendar .fc-toolbar { background: var(--green-deep); }\n#d-calendar .fc-button { font-size: 11px !important; padding: 3px 8px !important; }\n@keyframes numPop{0%{transform:scale(1);}40%{transform:scale(1.15);color:var(--green-mid);}100%{transform:scale(1);}}\n.pop-anim{animation:numPop .4s cubic-bezier(.34,1.56,.64,1) forwards;}\n.cal-evt-overlay{position:fixed;inset:0;background:rgba(0,0,0,0.85);z-index:9000;display:none;align-items:center;justify-content:center;padding-top:68px;}\n.cal-evt-overlay.show{display:flex;}\n.cal-evt-box{background:#ffffff;border-radius:14px;width:90%;max-width:440px;max-height:calc(100vh - 88px);overflow-y:auto;overflow-x:hidden;box-shadow:0 20px 60px rgba(0,0,0,0.5);animation:dashIn .25s ease;position:relative;z-index:9001;}\n.cal-evt-hdr{padding:14px 20px;background:var(--green-deep);color:white;display:flex;align-items:center;justify-content:space-between;}\n.cal-evt-hdr h2{margin:0;font-size:16px;font-family:'Cormorant Garamond',serif;font-weight:700;letter-spacing:1px;}\n.cal-evt-close{color:white;font-size:22px;font-weight:bold;cursor:pointer;opacity:.75;line-height:1;background:none;border:none;}\n.cal-evt-close:hover{opacity:1;}\n.cal-evt-body{padding:18px 20px;font-family:'Outfit',sans-serif;}\n.cal-evt-item{margin-bottom:11px;border-bottom:1px solid rgba(26,74,46,0.07);padding-bottom:9px;}\n.cal-evt-item:last-child{border-bottom:none;margin-bottom:0;}\n.cal-evt-lbl{font-weight:700;color:#aaa;font-size:10px;text-transform:uppercase;letter-spacing:1.2px;margin-bottom:3px;display:block;}\n.cal-evt-val{font-size:14px;color:#333;line-height:1.5;}\n.cal-evt-desc{background:rgba(26,74,46,0.04);padding:9px 11px;border-radius:6px;border-left:3px solid var(--green-mid);font-style:italic;font-size:13px;color:#555;}\n.cal-evt-no-data{text-align:center;padding:24px 0;color:var(--text-light);font-size:14px;}\n.dash-overlay{position:fixed;inset:0;background:rgba(0,0,0,0.85);z-index:8000;display:none;align-items:center;justify-content:center;padding-top:68px;}\n.dash-overlay.show{display:flex;}\n.dash-modal{background:var(--cream);border-radius:16px;width:96vw;max-width:1280px;max-height:calc(94vh - 68px);overflow-y:auto;overflow-x:hidden;display:flex;flex-direction:column;box-shadow:0 24px 80px rgba(0,0,0,0.35);animation:dashIn .3s ease;}\n@keyframes dashIn{from{transform:translateY(-30px);opacity:0}to{transform:translateY(0);opacity:1}}\n.d-header{background:var(--green-deep);color:white;padding:14px 22px;display:flex;align-items:center;justify-content:space-between;flex-shrink:0;}\n.d-header h1{margin:0;font-size:18px;font-weight:500;}\n.d-close-btn{background:rgba(255,255,255,0.15);border:1px solid rgba(255,255,255,0.3);color:white;border-radius:8px;padding:5px 14px;font-size:12px;cursor:pointer;transition:background .2s;}\n.d-close-btn:hover{background:rgba(255,255,255,0.25);}\n.d-city-banner{background:rgba(77,175,125,0.1);color:var(--green-deep);padding:10px 22px;font-size:14px;border-bottom:1px solid rgba(26,74,46,0.1);flex-shrink:0;}\n.d-city-banner strong{font-weight:700;}\n.d-content{display:flex;gap:16px;flex-wrap:wrap;padding:16px;overflow:visible;flex:1;}\n.d-panel{background:white;border-radius:10px;box-shadow:var(--shadow-sm);flex:1 1 45%;min-width:300px;overflow:visible;display:flex;flex-direction:column;}\n.d-panel-header{padding:10px 16px;background:rgba(26,74,46,0.04);border-bottom:1px solid rgba(26,74,46,0.08);font-weight:600;display:flex;align-items:center;color:var(--green-deep);font-size:13px;gap:7px;}\n#d-map-svg-wrap{height:420px;width:100%;position:relative;background:#c8dfc8;overflow:hidden;}\n#d-map-svg-wrap svg{width:100%;height:100%;display:block;}\n#d-map-tooltip{position:absolute;background:rgba(10,30,18,0.93);border:1px solid rgba(255,140,0,0.3);border-radius:7px;color:#fff;font-size:11px;padding:6px 10px;pointer-events:none;opacity:0;transition:opacity .15s;z-index:30;max-width:160px;}\n#d-map-tooltip strong{color:#ff9933;font-family:'Cormorant Garamond',serif;font-size:14px;display:block;}\n#d-calendar-container{padding:8px;height:auto;min-height:300px;overflow:visible;}\n.d-evt-modal{display:none;position:fixed;inset:0;z-index:9999;background:rgba(0,0,0,0.88);align-items:center;justify-content:center;}\n.d-evt-modal.show{display:flex;}\n.d-evt-box{background:#fff;border-radius:12px;width:80%;max-width:480px;overflow:hidden;box-shadow:0 10px 40px rgba(0,0,0,0.5);animation:dashIn .25s;position:relative;z-index:10000;}\n.d-evt-hdr{padding:14px 20px;background:var(--green-deep);color:white;position:relative;}\n.d-evt-hdr h2{margin:0;font-size:17px;font-weight:600;}\n.d-evt-close{color:white;position:absolute;right:14px;top:10px;font-size:24px;font-weight:bold;cursor:pointer;opacity:.75;line-height:1;}\n.d-evt-close:hover{opacity:1;}\n.d-evt-body{padding:18px 22px;}\n.d-evt-item{margin-bottom:12px;border-bottom:1px solid rgba(26,74,46,0.06);padding-bottom:9px;}\n.d-evt-item:last-child{border-bottom:none;}\n.d-evt-lbl{font-weight:700;color:#aaa;font-size:11px;text-transform:uppercase;letter-spacing:1px;margin-bottom:3px;display:block;}\n.d-evt-val{font-size:14px;color:#333;line-height:1.5;}\n.d-evt-desc{background:rgba(26,74,46,0.04);padding:9px;border-radius:5px;border-left:3px solid var(--green-mid);font-style:italic;}\n.loading-msg{font-size:11px;color:rgba(26,74,46,0.4);text-align:center;padding:20px;letter-spacing:1px;}\n\/* \u2500\u2500 Responsive & Zoom-safe layout fixes \u2500\u2500 *\/\n\n\/* Base: make sure body never clips *\/\nhtml, body {\n  overflow-x: hidden;\n  width: 100%;\n  min-width: 0;\n}\n\n\/* \u2500\u2500 Large Desktop \u2500\u2500 *\/\n@media (max-width: 1300px) {\n  .main-layout { grid-template-columns: 260px 1fr 300px; }\n}\n\n\/* \u2500\u2500 Medium Desktop \/ Landscape Tablet \u2500\u2500 *\/\n@media (max-width: 1100px) {\n  .main-layout { grid-template-columns: 240px 1fr 280px; }\n  .hdr-title { font-size: 13px; letter-spacing: 0.8px; }\n}\n\n\/* \u2500\u2500 Tablet (portrait + landscape) \u2500\u2500 *\/\n@media (max-width: 900px) {\n  .main-layout {\n    display: flex;\n    flex-direction: column;\n    height: auto;\n    overflow: visible;\n    min-height: 0;\n  }\n  .left-panel {\n    width: 100%;\n    max-height: none;\n    overflow: visible;\n    border-right: none;\n    border-bottom: 1px solid rgba(26,74,46,0.15);\n  }\n  .left-img-wrap { height: 220px; }\n  .map-panel {\n    width: 100%;\n    height: 420px;\n    min-height: 320px;\n    flex-shrink: 0;\n  }\n  .right-panel {\n    width: 100%;\n    max-height: none;\n    overflow: visible;\n    border-left: none;\n    border-top: 1px solid rgba(26,74,46,0.1);\n  }\n  .hdr-dates-badge { display: none; }\n  \/* Two-column stats on tablet *\/\n  .rlist { max-height: 300px; }\n}\n\n\/* \u2500\u2500 Small Tablet \/ Large Phone Landscape \u2500\u2500 *\/\n@media (max-width: 768px) {\n  .hdr { padding: 0 16px; height: 60px; }\n  .hdr-title { font-size: 12px; letter-spacing: 0.6px; }\n  .hdr-sub { font-size: 10px; letter-spacing: 1px; }\n  .map-panel { height: 380px; }\n  .left-img-wrap { height: 200px; }\n}\n\n\/* \u2500\u2500 Mobile \u2500\u2500 *\/\n@media (max-width: 600px) {\n  .hdr {\n    padding: 0 12px;\n    height: auto;\n    min-height: 56px;\n    flex-wrap: wrap;\n    gap: 6px;\n    padding-top: 8px;\n    padding-bottom: 8px;\n  }\n  .hdr-left { gap: 10px; }\n  .hdr-emblem { width: 38px; height: 26px; }\n  .hdr-title { font-size: 12px; letter-spacing: 0.6px; }\n  .hdr-sub { display: block; font-size: 8px; letter-spacing: 0.5px; }\n  .hdr-day-badge { display: none; }\n  .hdr-dates-badge { display: none; }\n  .btn-schedule { padding: 6px 12px; }\n  .btn-schedule span { display: none; }\n  .btn-invite { padding: 6px 10px; }\n  .btn-invite span { display: inline; font-size: 10px; }\n\n  .main-layout {\n    display: flex;\n    flex-direction: column;\n    height: auto;\n    overflow: visible;\n  }\n\n  .left-panel {\n    width: 100%;\n    order: 1;\n    overflow: visible;\n    max-height: none;\n    border-right: none;\n  }\n  .left-img-wrap { height: 180px; }\n  .left-img-caption { font-size: 14px; }\n\n  .map-panel {\n    width: 100%;\n    order: 2;\n    height: 300px;\n    min-height: 260px;\n  }\n\n  .right-panel {\n    width: 100%;\n    order: 3;\n    overflow: visible;\n    max-height: none;\n    border-left: none;\n  }\n\n  .map-overlay-badge {\n    padding: 5px 14px;\n    font-size: 11px;\n    bottom: 10px;\n  }\n  .map-badge-city { font-size: 13px; }\n\n  .live-city { font-size: 22px; }\n  .rp-section { padding: 12px; }\n  .cal-wrap { font-size: 10px; }\n\n  \/* Dashboard modal full-screen on mobile *\/\n  .dash-modal {\n    width: 100vw;\n    max-width: 100vw;\n    height: calc(100dvh - 56px);\n    max-height: calc(100dvh - 56px);\n    border-radius: 0;\n    overflow-y: auto;\n  }\n  .d-header { padding: 10px 14px; }\n  .d-header h1 { font-size: 14px !important; }\n  .d-city-banner { padding: 8px 14px; font-size: 12px; }\n  .d-content { flex-direction: column; gap: 10px; padding: 10px; overflow: visible; }\n  .d-panel { min-width: 0; flex: none; width: 100%; overflow: visible; border-radius: 10px; }\n  #d-map-svg-wrap { height: 260px; overflow: hidden; border-radius: 0 0 10px 10px; }\n  #d-calendar-container { height: auto !important; min-height: 0; padding: 6px; overflow: visible; }\n  .d-panel-header { font-size: 12px !important; padding: 8px 12px; }\n\n  \/* Mobile calendar button fix *\/\n  .fc .fc-button {\n    padding: 4px 8px !important;\n    font-size: 11px !important;\n  }\n  .fc .fc-toolbar-title { font-size: 12px !important; }\n  .fc .fc-toolbar { padding: 6px 8px; gap: 4px; }\n  .fc .fc-col-header-cell-cushion { font-size: 9px !important; padding: 3px 1px !important; }\n  .fc .fc-daygrid-day-number { font-size: 10px !important; padding: 2px !important; }\n  .fc .fc-toolbar-chunk { display: flex; align-items: center; gap: 3px; }\n  .fc .fc-button-group .fc-button { padding: 4px 6px !important; }\n\n  \/* Event modal on mobile *\/\n  .d-evt-box { width: 95%; }\n  .cal-evt-box { width: 95%; }\n}\n\n\/* \u2500\u2500 Very small phones \u2500\u2500 *\/\n@media (max-width: 380px) {\n  .hdr-title { font-size: 13px; }\n  .hdr-emblem { width: 32px; height: 22px; }\n  .map-panel { height: 260px; }\n  .left-img-wrap { height: 160px; }\n}\n\n\/* \u2500\u2500 Tablet dashboard modal \u2500\u2500 *\/\n@media (max-width: 900px) and (min-width: 601px) {\n  .dash-modal { width: 98vw; max-height: 96vh; }\n  .d-content { flex-direction: column; gap: 12px; }\n  .d-panel { width: 100%; min-width: 0; }\n  #d-map-svg-wrap { height: 320px; }\n  #d-calendar-container { height: auto; }\n  .d-header h1 { font-size: 15px !important; }\n}\n\n\/* \u2500\u2500 Zoom safety: ensure SVG maps always fill their containers \u2500\u2500 *\/\n#main-map-svg-wrap,\n#d-map-svg-wrap {\n  width: 100%;\n  height: 100%;\n  position: relative;\n  overflow: hidden;\n}\n#main-map-svg-wrap svg,\n#d-map-svg-wrap svg {\n  width: 100% !important;\n  height: 100% !important;\n  display: block;\n}\n\n\/* \u2500\u2500 Fix oversized FullCalendar event dots \/ map-pin emojis on mobile \u2500\u2500 *\/\n.fc-daygrid-event-dot {\n  width: 6px !important;\n  height: 6px !important;\n  border-radius: 50% !important;\n  border: 2px solid currentColor !important;\n  display: inline-block !important;\n  font-size: 0 !important;  \/* hide any emoji\/text inside dot *\/\n  line-height: 0 !important;\n  vertical-align: middle !important;\n}\n.fc-event-title {\n  font-size: 9px !important;\n  line-height: 1.2 !important;\n  overflow: hidden !important;\n  text-overflow: ellipsis !important;\n  white-space: nowrap !important;\n}\n.fc-daygrid-event {\n  font-size: 9px !important;\n  padding: 1px 3px !important;\n  border-radius: 3px !important;\n  overflow: hidden !important;\n}\n\/* Prevent emoji from becoming oversized *\/\n.fc .fc-daygrid-event-harness,\n.fc .fc-daygrid-dot-event {\n  font-size: 10px !important;\n  line-height: 1.2 !important;\n}\n\/* Fix d-header emoji *\/\n.d-header h1 {\n  font-size: clamp(13px, 3vw, 18px) !important;\n  font-weight: 500;\n}\n.d-panel-header {\n  font-size: clamp(11px, 2.5vw, 13px) !important;\n}\n\/* Prevent emojis from scaling up in headers *\/\n.d-header h1, .d-panel-header, .btn-schedule, .hdr-title {\n  font-variant-emoji: text;\n}\n.fc .fc-bg-event { opacity: 0.3; }\n\/* Prevent text-size adjust on zoom (iOS\/Android) *\/\nbody { -webkit-text-size-adjust: 100%; text-size-adjust: 100%; }\n\/* Fix FullCalendar dot sizes universally *\/\n.fc-daygrid-dot-event .fc-daygrid-event-dot,\n.fc-list-event-dot {\n  width: 6px !important; height: 6px !important;\n  min-width: 6px !important; min-height: 6px !important;\n  max-width: 6px !important; max-height: 6px !important;\n  border-radius: 50% !important;\n  font-size: 0 !important; line-height: 0 !important;\n}\n.fc .fc-list-event-graphic { width: 14px !important; padding-top: 5px !important; }\n<\/style>\n\n<div id=\"top\" style=\"position:absolute;top:0;left:0;height:0;width:0;overflow:hidden;\"><\/div>\n<header class=\"hdr\">\n  <div class=\"hdr-left\">\n    <div class=\"hdr-emblem\">\n      <svg width=\"50\" height=\"34\" viewBox=\"0 0 900 600\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\">\n        <rect width=\"900\" height=\"200\" fill=\"#FF9933\"><\/rect><rect y=\"200\" width=\"900\" height=\"200\" fill=\"#FFFFFF\"><\/rect>\n        <rect y=\"400\" width=\"900\" height=\"200\" fill=\"#138808\"><\/rect>\n        <circle cx=\"450\" cy=\"300\" r=\"90\" fill=\"none\" stroke=\"#000080\" stroke-width=\"8\"><\/circle>\n        <circle cx=\"450\" cy=\"300\" r=\"10\" fill=\"#000080\"><\/circle>\n        <g stroke=\"#000080\" stroke-width=\"3\">\n          <line x1=\"450\" y1=\"210\" x2=\"450\" y2=\"390\"><\/line><line x1=\"360\" y1=\"300\" x2=\"540\" y2=\"300\"><\/line>\n          <line x1=\"386\" y1=\"236\" x2=\"514\" y2=\"364\"><\/line><line x1=\"386\" y1=\"364\" x2=\"514\" y2=\"236\"><\/line>\n          <line x1=\"360\" y1=\"263\" x2=\"540\" y2=\"337\"><\/line><line x1=\"360\" y1=\"337\" x2=\"540\" y2=\"263\"><\/line>\n        <\/g>\n        <g fill=\"#000080\">\n          <circle cx=\"450\" cy=\"211\" r=\"5\"><\/circle><circle cx=\"514\" cy=\"236\" r=\"5\"><\/circle><circle cx=\"539\" cy=\"300\" r=\"5\"><\/circle>\n          <circle cx=\"514\" cy=\"364\" r=\"5\"><\/circle><circle cx=\"450\" cy=\"389\" r=\"5\"><\/circle><circle cx=\"386\" cy=\"364\" r=\"5\"><\/circle>\n          <circle cx=\"361\" cy=\"300\" r=\"5\"><\/circle><circle cx=\"386\" cy=\"236\" r=\"5\"><\/circle>\n        <\/g>\n      <\/svg>\n    <\/div>\n    <div>\n      <div class=\"hdr-title\">Bharat Climate Satyagraha Yatra<\/div>\n      <div class=\"hdr-sub\">100 Days Sacred Journey Across Bharat \u2014 Golden Quadrilateral<\/div>\n    <\/div>\n  <\/div>\n  <div class=\"hdr-right\">\n    <div class=\"hdr-dates-badge\">\n      <svg width=\"13\" height=\"13\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"rgba(255,255,255,0.7)\" stroke-width=\"2\" stroke-linecap=\"round\"><rect x=\"3\" y=\"4\" width=\"18\" height=\"18\" rx=\"2\"><\/rect><line x1=\"16\" y1=\"2\" x2=\"16\" y2=\"6\"><\/line><line x1=\"8\" y1=\"2\" x2=\"8\" y2=\"6\"><\/line><line x1=\"3\" y1=\"10\" x2=\"21\" y2=\"10\"><\/line><\/svg>\n      <span class=\"hdr-dates-txt\">May 13 \u2013 Aug 20, 2026<\/span>\n    <\/div>\n    <div class=\"hdr-day-badge\" id=\"hdr-day\">Day \u2014 of 100<\/div>\n    <button class=\"btn-schedule\" onclick=\"showCalendar()\">\n      <svg width=\"13\" height=\"13\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\"><rect x=\"3\" y=\"4\" width=\"18\" height=\"18\" rx=\"2\"><\/rect><line x1=\"16\" y1=\"2\" x2=\"16\" y2=\"6\"><\/line><line x1=\"8\" y1=\"2\" x2=\"8\" y2=\"6\"><\/line><line x1=\"3\" y1=\"10\" x2=\"21\" y2=\"10\"><\/line><\/svg>\n      <span>Today's Schedule<\/span>\n    <\/button>\n    <button class=\"btn-invite\" id=\"yatra-invite\" onclick=\"inviteYatra()\">\n      <svg width=\"13\" height=\"13\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\"><path d=\"M17 21v-2a4 4 0 0 0-4-4H5a4 4 0 0 0-4 4v2\"><\/path><circle cx=\"9\" cy=\"7\" r=\"4\"><\/circle><line x1=\"19\" y1=\"8\" x2=\"19\" y2=\"14\"><\/line><line x1=\"22\" y1=\"11\" x2=\"16\" y2=\"11\"><\/line><\/svg>\n      <span>Invite Yatra<\/span>\n    <\/button>\n  <\/div>\n<\/header>\n<div class=\"main-layout\">\n  <aside class=\"left-panel\">\n    <div style=\"padding:14px 16px 0;\">\n      <div style=\"font-size:9px;font-weight:700;letter-spacing:2px;color:rgba(255,255,255,0.4);text-transform:uppercase;margin-bottom:10px;\">Journey Stats<\/div>\n    <\/div>\n    <div style=\"padding:0 16px 14px;display:flex;flex-direction:column;gap:10px;\">\n      <div style=\"display:grid;grid-template-columns:1fr 1fr;gap:10px;\">\n        <div style=\"background:rgba(255,255,255,0.07);border:1px solid rgba(255,255,255,0.12);border-radius:10px;padding:12px;text-align:center;\">\n          <div style=\"position:relative;width:60px;height:60px;margin:0 auto 6px;\">\n            <svg width=\"60\" height=\"60\" viewBox=\"0 0 68 68\" style=\"transform:rotate(-90deg)\">\n              <circle class=\"circ-bg\" cx=\"34\" cy=\"34\" r=\"27\"><\/circle>\n              <circle class=\"circ-fg\" id=\"circ-done2\" cx=\"34\" cy=\"34\" r=\"27\" stroke-dasharray=\"169.6\" stroke-dashoffset=\"169.6\"><\/circle>\n            <\/svg>\n            <div style=\"position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:13px;font-weight:700;color:#fff;\" id=\"stat-done2\">0<\/div>\n          <\/div>\n          <div style=\"font-size:9px;font-weight:600;letter-spacing:1.5px;color:rgba(255,255,255,0.4);text-transform:uppercase;\">Days Done<\/div>\n        <\/div>\n        <div style=\"background:rgba(255,255,255,0.07);border:1px solid rgba(255,255,255,0.12);border-radius:10px;padding:12px;text-align:center;\">\n          <div style=\"position:relative;width:60px;height:60px;margin:0 auto 6px;\">\n            <svg width=\"60\" height=\"60\" viewBox=\"0 0 68 68\" style=\"transform:rotate(-90deg)\">\n              <circle class=\"circ-bg\" cx=\"34\" cy=\"34\" r=\"27\"><\/circle>\n              <circle class=\"circ-fg amber\" id=\"circ-left2\" cx=\"34\" cy=\"34\" r=\"27\" stroke-dasharray=\"169.6\" stroke-dashoffset=\"169.6\"><\/circle>\n            <\/svg>\n            <div style=\"position:absolute;inset:0;display:flex;align-items:center;justify-content:center;font-size:13px;font-weight:700;color:#fff;\" id=\"stat-left2\">100<\/div>\n          <\/div>\n          <div style=\"font-size:9px;font-weight:600;letter-spacing:1.5px;color:rgba(255,255,255,0.4);text-transform:uppercase;\">Days Left<\/div>\n        <\/div>\n      <\/div>\n      <div style=\"background:rgba(255,255,255,0.07);border:1px solid rgba(255,255,255,0.12);border-radius:10px;padding:10px 14px;display:flex;align-items:center;justify-content:space-between;\">\n        <div>\n          <div style=\"font-size:9px;font-weight:600;letter-spacing:1.5px;color:rgba(255,255,255,0.4);text-transform:uppercase;margin-bottom:3px;\">KMs Covered<\/div>\n          <div style=\"font-size:18px;font-weight:700;color:#fff;\" id=\"stat-km2\">0<\/div>\n        <\/div>\n        <svg width=\"28\" height=\"28\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"var(--green-light)\" stroke-width=\"1.5\"><circle cx=\"12\" cy=\"12\" r=\"10\"><\/circle><path d=\"M12 2a14.5 14.5 0 0 0 0 20 14.5 14.5 0 0 0 0-20\"><\/path><path d=\"M2 12h20\"><\/path><\/svg>\n      <\/div>\n      <div style=\"background:rgba(255,255,255,0.07);border:1px solid rgba(255,255,255,0.12);border-radius:10px;padding:10px 14px;display:flex;align-items:center;justify-content:space-between;\">\n        <div>\n          <div style=\"font-size:9px;font-weight:600;letter-spacing:1.5px;color:rgba(255,255,255,0.4);text-transform:uppercase;margin-bottom:3px;\">People Met<\/div>\n          <div style=\"font-size:18px;font-weight:700;color:#fff;\" id=\"stat-people2\">0<\/div>\n        <\/div>\n        <svg width=\"28\" height=\"28\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"var(--amber-light)\" stroke-width=\"1.5\"><path d=\"M17 21v-2a4 4 0 0 0-4-4H5a4 4 0 0 0-4 4v2\"><\/path><circle cx=\"9\" cy=\"7\" r=\"4\"><\/circle><path d=\"M23 21v-2a4 4 0 0 0-3-3.87\"><\/path><path d=\"M16 3.13a4 4 0 0 1 0 7.75\"><\/path><\/svg>\n      <\/div>\n    <\/div>\n    <div class=\"left-info\">\n      <div class=\"live-card\">\n        <div class=\"live-top\">\n          <div class=\"live-badge\" id=\"live-badge\"><div class=\"ldot\" id=\"live-dot\"><\/div><span id=\"live-txt\">LIVE<\/span><\/div>\n          <div class=\"day-pill\" id=\"day-pill\">Day \u2014<\/div>\n        <\/div>\n        <div class=\"live-city\" id=\"sb-city\">Loading\u2026<\/div>\n        <div class=\"live-date\" id=\"sb-date\">\u2014<\/div>\n      <\/div>\n      <div class=\"next-card\">\n        <div class=\"next-lbl\">Next Stop<\/div>\n        <div class=\"next-city\" id=\"sb-next\">\u2014<\/div>\n        <div class=\"next-when\" id=\"sb-next-when\">\u2014<\/div>\n      <\/div>\n      <div class=\"progress-wrap\">\n        <div class=\"progress-lbl\">Yatra Progress<\/div>\n        <div class=\"prog-bar-bg\"><div class=\"prog-bar-fill\" id=\"prog-fill\" style=\"width:1%\"><\/div><\/div>\n        <div class=\"prog-txt\" id=\"prog-txt\">Loading\u2026<\/div>\n      <\/div>\n      <div class=\"route-section\">\n        <div class=\"route-lbl\">Route<\/div>\n        <div class=\"rlist\" id=\"rlist\"><div class=\"loading-msg\">Loading route\u2026<\/div><\/div>\n      <\/div>\n    <\/div>\n  <\/aside>\n  <main class=\"map-panel\">\n    <div id=\"main-map-svg-wrap\">\n      <svg id=\"main-map-svg\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\"><\/svg>\n      <div id=\"map-tooltip\"><\/div>\n    <\/div>\n    <div class=\"map-overlay-badge\">\n      <div class=\"ldot\" style=\"background:#ff6600;animation:pulse-orange 1.2s ease-in-out infinite;\"><\/div>\n      <span class=\"map-badge-txt\">Currently at<\/span>\n      <span class=\"map-badge-city\" id=\"map-badge-city\">\u2014<\/span>\n    <\/div>\n  <\/main>\n  <aside class=\"right-panel\">\n    <div class=\"rp-section\">\n      <div class=\"rp-lbl\">India Route Map<\/div>\n      <div style=\"border-radius:10px;overflow:hidden;box-shadow:var(--shadow-sm);cursor:pointer;position:relative;line-height:0;\" onclick=\"document.getElementById('india-lb').style.display='flex'\">\n        <img src=\"http:\/\/thefiniteearth.org\/wp-content\/uploads\/2026\/04\/Asset-1.png.webp\" alt=\"India Map\" style=\"width: 100%; display: block; border-radius: 10px; transition: transform 0.3s; transform: scale(1);\" onmouseover=\"this.style.transform='scale(1.02)'\" onmouseout=\"this.style.transform='scale(1)'\" onerror=\"this.closest('div').style.display='none'\">\n        <div style=\"position:absolute;bottom:8px;right:8px;background:rgba(26,74,46,0.8);backdrop-filter:blur(4px);color:#fff;border-radius:20px;padding:4px 10px;font-size:10px;font-weight:600;pointer-events:none;\"><img role=\"img\" class=\"emoji\" alt=\"\ud83d\udd0d\" src=\"https:\/\/s.w.org\/images\/core\/emoji\/17.0.2\/svg\/1f50d.svg\"> Full View<\/div>\n      <\/div>\n    <\/div>\n    <div class=\"rp-section\">\n      <div class=\"rp-lbl\">Schedule<\/div>\n      <div class=\"cal-wrap\"><div id=\"inline-calendar\"><\/div><\/div>\n    <\/div>\n  <\/aside>\n<\/div>\n<div class=\"cal-evt-overlay\" id=\"cal-evt-overlay\" onclick=\"if(event.target===this)closeCalEvt()\">\n  <div class=\"cal-evt-box\">\n    <div class=\"cal-evt-hdr\"><h2 id=\"cal-evt-title\">Event Details<\/h2><button class=\"cal-evt-close\" onclick=\"closeCalEvt()\">\u00d7<\/button><\/div>\n    <div class=\"cal-evt-body\" id=\"cal-evt-body\"><div class=\"cal-evt-no-data\">No event data<\/div><\/div>\n    <div style=\"padding:0 20px 18px;\">\n      <a class=\"btn-invite-popup\" id=\"yatra-invite\" href=\"javascript:void(0)\" onclick=\"closeCalEvt();closeDash();inviteYatra();\">\n        <svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"display:inline-block;vertical-align:middle;margin-right:6px;\"><path d=\"M17 21v-2a4 4 0 0 0-4-4H5a4 4 0 0 0-4 4v2\"><\/path><circle cx=\"9\" cy=\"7\" r=\"4\"><\/circle><line x1=\"19\" y1=\"8\" x2=\"19\" y2=\"14\"><\/line><line x1=\"22\" y1=\"11\" x2=\"16\" y2=\"11\"><\/line><\/svg>\n        Take Action - Invite Yatra Now!\n      <\/a>\n    <\/div>\n  <\/div>\n<\/div>\n<div class=\"dash-overlay\" id=\"dash-overlay\" onclick=\"if(event.target===this)closeDash()\">\n  <div class=\"dash-modal\" id=\"dash-modal\" style=\"position:relative;\">\n    <div class=\"d-header\">\n      <h1><svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"display:inline-block;vertical-align:middle;margin-right:6px;flex-shrink:0\"><path d=\"M21 10c0 7-9 13-9 13s-9-6-9-13a9 9 0 0 1 18 0z\"><\/path><circle cx=\"12\" cy=\"10\" r=\"3\"><\/circle><\/svg>Live Yatra Tracking System<\/h1>\n      <button class=\"d-close-btn\" onclick=\"closeDash()\">\u2715 Close<\/button>\n    <\/div>\n    <div class=\"d-city-banner\">Current City: <strong id=\"d-current-city-text\">Loading...<\/strong><\/div>\n    <div class=\"d-content\">\n      <div class=\"d-panel\">\n        <div class=\"d-panel-header\"><svg width=\"13\" height=\"13\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"flex-shrink:0\"><path d=\"M21 10c0 7-9 13-9 13s-9-6-9-13a9 9 0 0 1 18 0z\"><\/path><circle cx=\"12\" cy=\"10\" r=\"3\"><\/circle><\/svg> Map<\/div>\n        <div id=\"d-map-svg-wrap\">\n          <svg id=\"d-map-svg\" xmlns=\"http:\/\/www.w3.org\/2000\/svg\"><\/svg>\n          <div id=\"d-map-tooltip\"><\/div>\n        <\/div>\n      <\/div>\n      <div class=\"d-panel\">\n        <div class=\"d-panel-header\"><svg width=\"13\" height=\"13\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"flex-shrink:0\"><rect x=\"3\" y=\"4\" width=\"18\" height=\"18\" rx=\"2\"><\/rect><line x1=\"16\" y1=\"2\" x2=\"16\" y2=\"6\"><\/line><line x1=\"8\" y1=\"2\" x2=\"8\" y2=\"6\"><\/line><line x1=\"3\" y1=\"10\" x2=\"21\" y2=\"10\"><\/line><\/svg> Calendar<\/div>\n        <div id=\"d-calendar-container\"><div id=\"d-calendar\"><\/div><\/div>\n      <\/div>\n    <\/div>\n    <div class=\"d-evt-modal\" id=\"d-evt-modal\">\n      <div class=\"d-evt-box\">\n        <div class=\"d-evt-hdr\"><span class=\"d-evt-close\" onclick=\"closeDEvt()\">\u00d7<\/span><h2 id=\"d-modal-name\">Event Details<\/h2><\/div>\n        <div class=\"d-evt-body\">\n          <div class=\"d-evt-item\"><span class=\"d-evt-lbl\">Hosted By<\/span><div class=\"d-evt-val\" id=\"d-modal-host\"><\/div><\/div>\n          <div class=\"d-evt-item\"><span class=\"d-evt-lbl\">Location<\/span><div class=\"d-evt-val\"><span id=\"d-modal-venue\"><\/span>, <span id=\"d-modal-city\"><\/span><\/div><\/div>\n          <div class=\"d-evt-item\" style=\"display:flex;gap:20px;\">\n            <div><span class=\"d-evt-lbl\">Date<\/span><div class=\"d-evt-val\" id=\"d-modal-date\"><\/div><\/div>\n            <div><span class=\"d-evt-lbl\">Time<\/span><div class=\"d-evt-val\" id=\"d-modal-time\"><\/div><\/div>\n          <\/div>\n          <div class=\"d-evt-item\"><span class=\"d-evt-lbl\">Description<\/span><div class=\"d-evt-val d-evt-desc\" id=\"d-modal-desc\"><\/div><\/div>\n        <\/div>\n        <div style=\"padding:0 22px 18px;\">\n          <a class=\"btn-invite-popup\" href=\"javascript:void(0)\" onclick=\"closeDEvt();closeDash();inviteYatra();\">\n            <svg width=\"14\" height=\"14\" viewBox=\"0 0 24 24\" fill=\"none\" stroke=\"currentColor\" stroke-width=\"2\" stroke-linecap=\"round\" stroke-linejoin=\"round\" style=\"display:inline-block;vertical-align:middle;margin-right:6px;\"><path d=\"M17 21v-2a4 4 0 0 0-4-4H5a4 4 0 0 0-4 4v2\"><\/path><circle cx=\"9\" cy=\"7\" r=\"4\"><\/circle><line x1=\"19\" y1=\"8\" x2=\"19\" y2=\"14\"><\/line><line x1=\"22\" y1=\"11\" x2=\"16\" y2=\"11\"><\/line><\/svg>\n            Take Action - Invite Yatra Now!\n          <\/a>\n        <\/div>\n      <\/div>\n    <\/div>\n  <\/div>\n<\/div>\n<div id=\"india-lb\" onclick=\"this.style.display='none'\" style=\"display:none;position:fixed;inset:0;background:rgba(0,0,0,0.85);z-index:700;align-items:center;justify-content:center;backdrop-filter:blur(6px);\">\n  <div onclick=\"event.stopPropagation()\" style=\"position:relative;background:#0a1e0f;border-radius:14px;padding:18px;max-width:90vw;max-height:92vh;display:flex;flex-direction:column;align-items:center;box-shadow:0 20px 80px rgba(0,0,0,0.5);\">\n    <button onclick=\"document.getElementById('india-lb').style.display='none'\" style=\"position:absolute;top:8px;right:10px;background:rgba(255,255,255,0.15);border:1px solid rgba(255,255,255,0.25);color:#fff;border-radius:50%;width:30px;height:30px;font-size:15px;cursor:pointer;\">\u2715<\/button>\n    <img src=\"http:\/\/thefiniteearth.org\/wp-content\/uploads\/2026\/04\/Asset-1.png.webp\" alt=\"India Route Map\" style=\"max-width:100%;max-height:80vh;border-radius:8px;display:block;\">\n    <div style=\"text-align:center;margin-top:10px;color:rgba(255,255,255,0.6);font-size:12px;\">Golden Quadrilateral Yatra Route \u2014 Bharat<\/div>\n  <\/div>\n<\/div>\n<code class=\"tve_js_placeholder\">[tcb-script src=\"https:\/\/cdn.jsdelivr.net\/npm\/fullcalendar@5.11.3\/main.min.js\"][\/tcb-script]<\/code>\n<code class=\"tve_js_placeholder\">[tcb-script src=\"https:\/\/cdnjs.cloudflare.com\/ajax\/libs\/d3\/7.9.0\/d3.min.js\"][\/tcb-script]<\/code>\n<code class=\"tve_js_placeholder\">[tcb-script]\nif ('scrollRestoration' in history) history.scrollRestoration = 'manual';\n\/\/ Remove any hash from URL on load to prevent scrolling to #take-action\nif(window.location.hash) { history.replaceState(null, '', window.location.pathname + window.location.search); }\nwindow.scrollTo(0,0);\ndocument.addEventListener('DOMContentLoaded',()=&gt;{ window.scrollTo(0,0); });\nwindow.addEventListener('load',()=&gt;{ window.scrollTo(0,0); setTimeout(()=&gt;window.scrollTo(0,0),200); });\n\nfunction inviteYatra(){\n\tconsole.log(\"hello\");\n    var target = document.getElementById(\"take-action-invite-yatra-now\");\n    \n    if (target) {\n        window.scrollTo({\n            top: target.offsetTop,\n            behavior: \"smooth\"\n        });\n    }\n\n\t\n  try{\n    \/\/ Try direct element scroll in parent window\n    var topDoc=window.top.document;\n    var el=topDoc.getElementById('take-action-invite-yatra-now');\n    if(el){el.scrollIntoView({behavior:'smooth',block:'start'});return;}\n    \/\/ Try anchor link approach - does not reload page\n    var a=topDoc.createElement('a');\n    a.href='#take-action-invite-yatra-now';\n    topDoc.body.appendChild(a);\n    a.click();\n    topDoc.body.removeChild(a);\n  }catch(e){\n    \/\/ cross-origin: open same page at anchor in same tab\n    window.top.location.href='https:\/\/thefiniteearth.org\/100-days-esy\/?preview=true#take-action-invite-yatra-now';\n  }\n}\nconst API_URL='https:\/\/script.google.com\/macros\/s\/AKfycbwG5S7pytIy4PYRNluekHx8wgn6VPfqI9FJdOHoonbX9CrSO56IL8MGUikkq1V-wALq4w\/exec';\nconst GQ_ROUTE=[\n  {name:'Delhi',lat:28.6139,lon:77.2090},{name:'Gurugram',lat:28.4595,lon:77.0266},\n  {name:'Manesar',lat:28.3562,lon:76.9383},{name:'Neemrana',lat:27.9747,lon:76.3844},\n  {name:'Alwar',lat:27.5530,lon:76.6346},{name:'Jaipur',lat:26.9124,lon:75.7873},\n  {name:'Ajmer',lat:26.4499,lon:74.6399},{name:'Bhilwara',lat:25.3474,lon:74.6339},\n  {name:'Chittorgarh',lat:24.8887,lon:74.6269},{name:'Udaipur',lat:24.5854,lon:73.7125},\n  {name:'Ahmedabad',lat:23.0225,lon:72.5714},{name:'Vadodara',lat:22.3072,lon:73.1812},\n  {name:'Bharuch',lat:21.7051,lon:72.9959},{name:'Surat',lat:21.1702,lon:72.8311},\n  {name:'Vapi',lat:20.3749,lon:72.9057},{name:'Mumbai',lat:19.0760,lon:72.8777},\n  {name:'Pune',lat:18.5204,lon:73.8567},{name:'Satara',lat:17.6805,lon:74.0183},\n  {name:'Kolhapur',lat:16.7050,lon:74.2433},{name:'Belagavi',lat:15.8497,lon:74.4977},\n  {name:'Dharwad',lat:15.4589,lon:75.0078},{name:'Hubballi',lat:15.3647,lon:75.1240},\n  {name:'Davanagere',lat:14.4644,lon:75.9218},{name:'Chitradurga',lat:14.2296,lon:76.3981},\n  {name:'Tumakuru',lat:13.3379,lon:77.1173},{name:'Bengaluru',lat:12.9716,lon:77.5946},\n  {name:'Hosur',lat:12.7409,lon:77.8253},{name:'Krishnagiri',lat:12.5266,lon:78.2138},\n  {name:'Vellore',lat:12.9165,lon:79.1325},{name:'Chennai',lat:13.0827,lon:80.2707},\n  {name:'Nellore',lat:14.4426,lon:79.9865},{name:'Ongole',lat:15.5057,lon:80.0499},\n  {name:'Vijayawada',lat:16.5062,lon:80.6480},{name:'Rajamahendravaram',lat:17.0005,lon:81.8040},\n  {name:'Visakhapatnam',lat:17.6868,lon:83.2185},{name:'Srikakulam',lat:18.2949,lon:83.8938},\n  {name:'Berhampur',lat:19.3150,lon:84.7941},{name:'Bhubaneswar',lat:20.2961,lon:85.8245},\n  {name:'Cuttack',lat:20.4625,lon:85.8830},{name:'Balasore',lat:21.4927,lon:86.9316},\n  {name:'Kharagpur',lat:22.3460,lon:87.2319},{name:'Kolkata',lat:22.5726,lon:88.3639},\n  {name:'Durgapur',lat:23.5204,lon:87.3119},{name:'Asansol',lat:23.6739,lon:86.9524},\n  {name:'Dhanbad',lat:23.7957,lon:86.4304},{name:'Hazaribagh',lat:23.9925,lon:85.3637},\n  {name:'Gaya',lat:24.7955,lon:85.0002},{name:'Sasaram',lat:24.9474,lon:84.0317},\n  {name:'Prayagraj',lat:25.4358,lon:81.8463},{name:'Kanpur',lat:26.4499,lon:80.3319},\n  {name:'Agra',lat:27.1767,lon:78.0081},{name:'Mathura',lat:27.4924,lon:77.6737},\n  {name:'Faridabad',lat:28.4082,lon:77.3178},{name:'Delhi',lat:28.6139,lon:77.2090},\n];\nconst GQ_MAP={};GQ_ROUTE.forEach(r=&gt;{GQ_MAP[r.name.toLowerCase()]=r;});\n\n\/* \u2500\u2500 India Background Cities (State Capitals + Major Cities) \u2500\u2500 *\/\nconst INDIA_BG_CITIES = [\n  \/\/ State Capitals\n  {n:'Amaravati',lat:16.5193,lon:80.5180,cap:true},\n  {n:'Itanagar',lat:27.0844,lon:93.6053,cap:true},\n  {n:'Dispur',lat:26.1433,lon:91.7898,cap:true},\n  {n:'Patna',lat:25.5941,lon:85.1376,cap:true},\n  {n:'Raipur',lat:21.2514,lon:81.6296,cap:true},\n  {n:'Panaji',lat:15.4989,lon:73.8278,cap:true},\n  {n:'Gandhinagar',lat:23.2156,lon:72.6369,cap:true},\n  {n:'Chandigarh',lat:30.7333,lon:76.7794,cap:true},\n  {n:'Shimla',lat:31.1048,lon:77.1734,cap:true},\n  {n:'Ranchi',lat:23.3441,lon:85.3096,cap:true},\n  {n:'Bengaluru',lat:12.9716,lon:77.5946,cap:true},\n  {n:'Thiruvananthapuram',lat:8.5241,lon:76.9366,cap:true},\n  {n:'Bhopal',lat:23.2599,lon:77.4126,cap:true},\n  {n:'Mumbai',lat:19.0760,lon:72.8777,cap:true},\n  {n:'Imphal',lat:24.8170,lon:93.9368,cap:true},\n  {n:'Shillong',lat:25.5788,lon:91.8933,cap:true},\n  {n:'Aizawl',lat:23.7307,lon:92.7173,cap:true},\n  {n:'Kohima',lat:25.6751,lon:94.1086,cap:true},\n  {n:'Bhubaneswar',lat:20.2961,lon:85.8245,cap:true},\n  {n:'Chandigarh',lat:30.7333,lon:76.7794,cap:true},\n  {n:'Jaipur',lat:26.9124,lon:75.7873,cap:true},\n  {n:'Gangtok',lat:27.3314,lon:88.6138,cap:true},\n  {n:'Chennai',lat:13.0827,lon:80.2707,cap:true},\n  {n:'Hyderabad',lat:17.3850,lon:78.4867,cap:true},\n  {n:'Agartala',lat:23.8315,lon:91.2868,cap:true},\n  {n:'Lucknow',lat:26.8467,lon:80.9462,cap:true},\n  {n:'Dehradun',lat:30.3165,lon:78.0322,cap:true},\n  {n:'Kolkata',lat:22.5726,lon:88.3639,cap:true},\n  {n:'Delhi',lat:28.6139,lon:77.2090,cap:true},\n  \/\/ Major cities\n  {n:'Srinagar',lat:34.0837,lon:74.7973},\n  {n:'Jammu',lat:32.7266,lon:74.8570},\n  {n:'Leh',lat:34.1526,lon:77.5771},\n  {n:'Amritsar',lat:31.6340,lon:74.8723},\n  {n:'Ludhiana',lat:30.9010,lon:75.8573},\n  {n:'Jalandhar',lat:31.3260,lon:75.5762},\n  {n:'Ambala',lat:30.3782,lon:76.7767},\n  {n:'Hisar',lat:29.1492,lon:75.7217},\n  {n:'Rohtak',lat:28.8955,lon:76.6066},\n  {n:'Gurugram',lat:28.4595,lon:77.0266},\n  {n:'Noida',lat:28.5355,lon:77.3910},\n  {n:'Ghaziabad',lat:28.6692,lon:77.4538},\n  {n:'Meerut',lat:28.9845,lon:77.7064},\n  {n:'Aligarh',lat:27.8974,lon:78.0880},\n  {n:'Agra',lat:27.1767,lon:78.0081},\n  {n:'Mathura',lat:27.4924,lon:77.6737},\n  {n:'Bareilly',lat:28.3670,lon:79.4304},\n  {n:'Moradabad',lat:28.8389,lon:78.7769},\n  {n:'Varanasi',lat:25.3176,lon:82.9739},\n  {n:'Allahabad',lat:25.4358,lon:81.8463},\n  {n:'Kanpur',lat:26.4499,lon:80.3319},\n  {n:'Gorakhpur',lat:26.7606,lon:83.3732},\n  {n:'Jhansi',lat:25.4484,lon:78.5685},\n  {n:'Gwalior',lat:26.2183,lon:78.1828},\n  {n:'Indore',lat:22.7196,lon:75.8577},\n  {n:'Jabalpur',lat:23.1815,lon:79.9864},\n  {n:'Ujjain',lat:23.1793,lon:75.7849},\n  {n:'Surat',lat:21.1702,lon:72.8311},\n  {n:'Ahmedabad',lat:23.0225,lon:72.5714},\n  {n:'Vadodara',lat:22.3072,lon:73.1812},\n  {n:'Rajkot',lat:22.3039,lon:70.8022},\n  {n:'Bhavnagar',lat:21.7645,lon:72.1519},\n  {n:'Jamnagar',lat:22.4707,lon:70.0577},\n  {n:'Jodhpur',lat:26.2389,lon:73.0243},\n  {n:'Udaipur',lat:24.5854,lon:73.7125},\n  {n:'Kota',lat:25.2138,lon:75.8648},\n  {n:'Ajmer',lat:26.4499,lon:74.6399},\n  {n:'Bikaner',lat:28.0229,lon:73.3119},\n  {n:'Pune',lat:18.5204,lon:73.8567},\n  {n:'Nagpur',lat:21.1458,lon:79.0882},\n  {n:'Nashik',lat:19.9975,lon:73.7898},\n  {n:'Aurangabad',lat:19.8762,lon:75.3433},\n  {n:'Solapur',lat:17.6805,lon:75.9064},\n  {n:'Kolhapur',lat:16.7050,lon:74.2433},\n  {n:'Amravati',lat:20.9374,lon:77.7796},\n  {n:'Vizag',lat:17.6868,lon:83.2185},\n  {n:'Vijayawada',lat:16.5062,lon:80.6480},\n  {n:'Tirupati',lat:13.6288,lon:79.4192},\n  {n:'Guntur',lat:16.3067,lon:80.4365},\n  {n:'Warangal',lat:17.9784,lon:79.5941},\n  {n:'Nellore',lat:14.4426,lon:79.9865},\n  {n:'Coimbatore',lat:11.0168,lon:76.9558},\n  {n:'Madurai',lat:9.9252,lon:78.1198},\n  {n:'Tiruchirappalli',lat:10.7905,lon:78.7047},\n  {n:'Salem',lat:11.6643,lon:78.1460},\n  {n:'Tirunelveli',lat:8.7139,lon:77.7567},\n  {n:'Kochi',lat:9.9312,lon:76.2673},\n  {n:'Kozhikode',lat:11.2588,lon:75.7804},\n  {n:'Thrissur',lat:10.5276,lon:76.2144},\n  {n:'Kollam',lat:8.8932,lon:76.6141},\n  {n:'Mysuru',lat:12.2958,lon:76.6394},\n  {n:'Hubli',lat:15.3647,lon:75.1240},\n  {n:'Mangaluru',lat:12.9141,lon:74.8560},\n  {n:'Belagavi',lat:15.8497,lon:74.4977},\n  {n:'Davangere',lat:14.4644,lon:75.9218},\n  {n:'Guwahati',lat:26.1445,lon:91.7362},\n  {n:'Silchar',lat:24.8333,lon:92.7789},\n  {n:'Dibrugarh',lat:27.4728,lon:94.9120},\n  {n:'Siliguri',lat:26.7271,lon:88.3953},\n  {n:'Asansol',lat:23.6739,lon:86.9524},\n  {n:'Durgapur',lat:23.5204,lon:87.3119},\n  {n:'Howrah',lat:22.5958,lon:88.2636},\n  {n:'Kharagpur',lat:22.3460,lon:87.2319},\n  {n:'Dhanbad',lat:23.7957,lon:86.4304},\n  {n:'Jamshedpur',lat:22.8046,lon:86.2029},\n  {n:'Bokaro',lat:23.6693,lon:86.1511},\n  {n:'Muzaffarpur',lat:26.1209,lon:85.3647},\n  {n:'Gaya',lat:24.7955,lon:85.0002},\n  {n:'Bhagalpur',lat:25.2425,lon:86.9842},\n  {n:'Darbhanga',lat:26.1542,lon:85.8918},\n  {n:'Bilaspur',lat:22.0797,lon:82.1409},\n  {n:'Korba',lat:22.3595,lon:82.7501},\n  {n:'Bhopal',lat:23.2599,lon:77.4126},\n  {n:'Shivpuri',lat:25.4231,lon:77.6577},\n  {n:'Rewa',lat:24.5362,lon:81.3037},\n  {n:'Satna',lat:24.5854,lon:80.8322},\n  {n:'Prayagraj',lat:25.4358,lon:81.8463},\n  {n:'Puducherry',lat:11.9416,lon:79.8083},\n  {n:'Vellore',lat:12.9165,lon:79.1325},\n  {n:'Erode',lat:11.3410,lon:77.7172},\n  {n:'Kakinada',lat:16.9891,lon:82.2475},\n  {n:'Rajahmundry',lat:17.0005,lon:81.8040},\n  {n:'Shillong',lat:25.5788,lon:91.8933},\n  {n:'Imphal',lat:24.8170,lon:93.9368},\n  {n:'Agartala',lat:23.8315,lon:91.2868},\n  {n:'Aizawl',lat:23.7307,lon:92.7173},\n  {n:'Dimapur',lat:25.9010,lon:93.7360},\n  {n:'Udaipur',lat:24.5854,lon:73.7125},\n  {n:'Alwar',lat:27.5530,lon:76.6346},\n  {n:'Bharatpur',lat:27.2152,lon:77.4938},\n  {n:'Pali',lat:25.7711,lon:73.3234},\n  {n:'Haldwani',lat:29.2183,lon:79.5130},\n  {n:'Roorkee',lat:29.8543,lon:77.8880},\n  {n:'Haridwar',lat:29.9457,lon:78.1642},\n  {n:'Rishikesh',lat:30.0869,lon:78.2676},\n];\n\nlet cities=[],cur=0,allYatraData=[];\nlet inlineCal=null;\nlet mainProjection=null, dashProjection=null;\n\n\/* \u2500\u2500 helper: append a city-name label to a D3 selection \u2500\u2500 *\/\nfunction appendCityLabel(sel, px, py, cityName, status, fromSheet) {\n  const isC = status==='current';\n  const isV = status==='visited';\n  const isSheet = !!fromSheet;\n\n  \/\/ For current city: animated pulsing label\n  if(isC){\n    const lbl = sel.append('text')\n      .attr('x', px)\n      .attr('y', py - 16)\n      .attr('text-anchor','middle')\n      .attr('font-size', 11)\n      .attr('font-weight','800')\n      .attr('font-family',\"'Outfit',sans-serif\")\n      .attr('fill','#e53935')\n      .attr('paint-order','stroke')\n      .attr('stroke','rgba(255,255,255,0.98)')\n      .attr('stroke-width', 3.5)\n      .attr('stroke-linejoin','round')\n      .attr('pointer-events','none')\n      .attr('letter-spacing','0.5')\n      .text(cityName);\n\n    \/\/ animate label opacity for live pulse effect\n    function animateLbl(){\n      lbl.transition().duration(800).attr('opacity',0.6)\n        .transition().duration(800).attr('opacity',1)\n        .on('end', animateLbl);\n    }\n    animateLbl();\n    return;\n  }\n\n  \/\/ Sheet-updated cities: orange, slightly bold\n  if(isSheet){\n    sel.append('text')\n      .attr('x', px)\n      .attr('y', py + 10)\n      .attr('text-anchor','middle')\n      .attr('font-size', 6.5)\n      .attr('font-weight','600')\n      .attr('font-family',\"'Outfit',sans-serif\")\n      .attr('fill', isV ? '#cc6600' : '#ff8c00')\n      .attr('paint-order','stroke')\n      .attr('stroke','rgba(255,255,255,0.95)')\n      .attr('stroke-width', 2.5)\n      .attr('stroke-linejoin','round')\n      .attr('pointer-events','none')\n      .text(cityName);\n    return;\n  }\n\n  \/\/ GQ route cities (not sheet): small, subtle grey\n  sel.append('text')\n    .attr('x', px)\n    .attr('y', py + 9)\n    .attr('text-anchor','middle')\n    .attr('font-size', 6.5)\n    .attr('font-weight','400')\n    .attr('font-family',\"'Outfit',sans-serif\")\n    .attr('fill', isV ? 'rgba(26,74,46,0.6)' : 'rgba(100,70,0,0.5)')\n    .attr('paint-order','stroke')\n    .attr('stroke','rgba(255,255,255,0.85)')\n    .attr('stroke-width', 2)\n    .attr('stroke-linejoin','round')\n    .attr('pointer-events','none')\n    .text(cityName);\n}\n\n\/* \u2500\u2500 Animated counter \u2500\u2500 *\/\nconst _cs={};\nfunction fmtNum(v){if(v&gt;=10000)return(v\/1000).toFixed(1)+'K';return String(Math.round(v));}\nfunction animateCounter(elId,targetNum,unit){\n  const el=document.getElementById(elId);if(!el)return;\n  const target=parseFloat(String(targetNum).replace(\/[^0-9.]\/g,''));\n  if(isNaN(target))return;\n  const prev=_cs[elId]||0;if(prev===target){el.textContent=fmtNum(target)+(unit||'');return;}\n  _cs[elId]=target;const dur=600,t0=performance.now();\n  el.classList.remove('pop-anim');void el.offsetWidth;el.classList.add('pop-anim');\n  setTimeout(()=&gt;el.classList.remove('pop-anim'),450);\n  function step(now){const t=Math.min((now-t0)\/dur,1),e=1-Math.pow(1-t,3),v=prev+(target-prev)*e;el.textContent=fmtNum(v)+(unit||'');if(t&lt;1)requestAnimationFrame(step);}\n  requestAnimationFrame(step);\n}\nfunction setCircle(id,pct){\n  const el=document.getElementById(id);if(!el)return;\n  const r=27,c=2*Math.PI*r,offset=c-(pct\/100)*c;\n  el.style.strokeDasharray=c;el.style.strokeDashoffset=offset;\n}\nfunction toISO(d){return`${d.getFullYear()}-${String(d.getMonth()+1).padStart(2,'0')}-${String(d.getDate()).padStart(2,'0')}`;}\nfunction todayISO(){return toISO(new Date());}\nfunction parseISO(s){if(!s)return null;const d=new Date(s);return isNaN(d)?null:d;}\nfunction formatDate(iso){const d=parseISO(iso);return d?d.toLocaleDateString('en-IN',{day:'numeric',month:'short'}):iso;}\nfunction dNorm(v){\n  if(!v)return null;\n  if(typeof v==='string'&amp;&amp;\/^\\d{4}-\\d{2}-\\d{2}$\/.test(v))return v;\n  try{const d=new Date(v);if(!isNaN(d.getTime()))return`${d.getFullYear()}-${String(d.getMonth()+1).padStart(2,'0')}-${String(d.getDate()).padStart(2,'0')}`;}catch(e){}\n  return null;\n}\nfunction dFmt(s){const n=dNorm(s);return n?new Date(n).toLocaleDateString('en-US',{year:'numeric',month:'long',day:'numeric'}):s;}\nfunction getCurrentIndex(list){\n  const t=todayISO();if(!list.length)return 0;\n  if(t&lt;list[0].iso)return 0;if(t&gt;=list[list.length-1].iso)return list.length-1;\n  let idx=0;for(let i=0;i&lt;list.length;i++){if(list[i].iso&lt;=t)idx=i;}return idx;\n}\nfunction buildCitiesFromSheet(data){\n  if(!data||!data.length)return null;\n  const seen={},list=[];\n  data.forEach(item=&gt;{\n    const iso=dNorm(item.Date);if(!iso)return;if(seen[iso])return;\n    const rawCity=(item.City||'').trim();if(!rawCity)return;\n    const isBreak=rawCity.toLowerCase()==='break'||(item['Status']||'').toLowerCase()==='break'||(item['Type']||'').toLowerCase()==='break';\n    let lat=parseFloat(item.Latitude),lon=parseFloat(item.Longitude);\n    if(isNaN(lat)||isNaN(lon)){\n      if(isBreak){const p=list[list.length-1];if(!p)return;lat=p.lat;lon=p.lon;}\n      else{const gq=GQ_MAP[rawCity.toLowerCase()];if(!gq)return;lat=gq.lat;lon=gq.lon;}\n    }\n    seen[iso]=true;\n    list.push({name:isBreak?'Break':rawCity,lat,lon,iso,dateStr:formatDate(iso),isBreak,_fromSheet:true});\n  });\n  if(!list.length)return null;\n  list.sort((a,b)=&gt;a.iso.localeCompare(b.iso));\n  const s=parseISO(list[0].iso);\n  list.forEach((c,i)=&gt;{const d=parseISO(c.iso);c.day=s&amp;&amp;d?Math.round((d-s)\/86400000)+1:i+1;c.idx=i;});\n  return list;\n}\nfunction buildCitiesFromGQ(){\n  const S=new Date('2026-05-13'),T=100,step=T\/(GQ_ROUTE.length-1);\n  return GQ_ROUTE.map((c,i)=&gt;{\n    const dn=Math.round(i*step)+1,d=new Date(S);d.setDate(d.getDate()+dn-1);\n    const iso=toISO(d);return{...c,day:dn,iso,dateStr:formatDate(iso),idx:i};\n  });\n}\n\nconst INDIA_GEOJSON_URL = 'https:\/\/cdn.jsdelivr.net\/gh\/udit-001\/india-maps-data@ef25ebc\/geojson\/india.geojson';\nlet indiaGeoJSON = null;\nasync function loadIndiaGeoJSON() {\n  if (indiaGeoJSON) return indiaGeoJSON;\n  try {\n    const res = await fetch(INDIA_GEOJSON_URL);\n    const data = await res.json();\n    indiaGeoJSON = data;\n    return indiaGeoJSON;\n  } catch(e) {\n    console.warn('Primary GeoJSON failed, trying fallback:', e);\n    try {\n      const fallbackRes = await fetch('https:\/\/raw.githubusercontent.com\/datasets\/geo-countries\/master\/data\/countries.geojson');\n      const fallbackData = await fallbackRes.json();\n      indiaGeoJSON = {\n        type: 'FeatureCollection',\n        features: fallbackData.features.filter(f =&gt;\n          (f.properties.ADMIN === 'India' || f.properties.ISO_A3 === 'IND')\n        )\n      };\n      return indiaGeoJSON;\n    } catch(fbErr) {\n      console.error('All GeoJSON sources failed:', fbErr);\n      return null;\n    }\n  }\n}\nfunction makeProjection(svgEl) {\n  const rect = svgEl.getBoundingClientRect();\n  const W = rect.width || svgEl.parentElement.clientWidth || 500;\n  const H = rect.height || svgEl.parentElement.clientHeight || 500;\n  const proj = d3.geoMercator().center([82.5, 22]).scale(1).translate([W\/2, H\/2]);\n  const topLeft = proj([68.0, 37.5]);\n  const bottomRight = proj([97.5, 6.5]);\n  const kX = (W * 0.92) \/ (bottomRight[0] - topLeft[0]);\n  const kY = (H * 0.92) \/ (bottomRight[1] - topLeft[1]);\n  const k = Math.min(kX, kY);\n  proj.scale(k);\n  const c = proj([82.5, 22]);\n  proj.translate([W\/2 + (W\/2 - c[0]), H\/2 + (H\/2 - c[1])]);\n  return proj;\n}\nfunction latLonToXY(proj, lat, lon) {\n  const pt = proj([lon, lat]);\n  return pt ? {x: pt[0], y: pt[1]} : null;\n}\n\n\/* \u2500\u2500 renderD3Map \u2014 used by dashboard map \u2500\u2500 *\/\nfunction renderD3Map(svgId, tooltipId, citiesList, currentIdx, extraPoints) {\n  const svgEl = document.getElementById(svgId);\n  if (!svgEl) return;\n  const svg = d3.select('#'+svgId);\n  svg.selectAll('*').remove();\n  const rect = svgEl.getBoundingClientRect();\n  const W = rect.width || svgEl.parentElement.clientWidth || 500;\n  const H = rect.height || svgEl.parentElement.clientHeight || 500;\n  svg.attr('viewBox', `0 0 ${W} ${H}`);\n  const proj = makeProjection(svgEl);\n  if (svgId === 'main-map-svg') mainProjection = proj;\n  else dashProjection = proj;\n  const pathGen = d3.geoPath().projection(proj);\n  const tooltip = document.getElementById(tooltipId);\n  svg.append('rect').attr('width',W).attr('height',H).attr('fill','#b8d4e8');\n  if (indiaGeoJSON &amp;&amp; indiaGeoJSON.features &amp;&amp; indiaGeoJSON.features.length) {\n    svg.selectAll('.india-path')\n      .data(indiaGeoJSON.features)\n      .enter().append('path')\n      .attr('class','india-path')\n      .attr('d', pathGen)\n      .attr('fill','#d4ebd4')\n      .attr('stroke','#5a9a6a')\n      .attr('stroke-width', 1.0);\n  } else {\n    svg.append('rect').attr('x',W*0.05).attr('y',H*0.05).attr('width',W*0.9).attr('height',H*0.9)\n      .attr('rx',8).attr('fill','#d4ebd4').attr('stroke','#5a9a6a').attr('stroke-width',1.5);\n    svg.append('text').attr('x',W\/2).attr('y',H\/2).attr('text-anchor','middle')\n      .attr('fill','#5a9a6a').attr('font-size',13).attr('font-family','Outfit,sans-serif')\n      .text('India Map Loading...');\n  }\n  function cityPt(c){ return latLonToXY(proj, c.lat, c.lon); }\n  const donePts = [];\n  for(let i=0; i&lt;=currentIdx; i++){\n    const p = cityPt(citiesList[i]);\n    if(p &amp;&amp; (donePts.length===0 || donePts[donePts.length-1][0]!==p.x || donePts[donePts.length-1][1]!==p.y))\n      donePts.push([p.x, p.y]);\n  }\n  if(donePts.length&gt;1){\n    svg.append('polyline')\n      .attr('points', donePts.map(p=&gt;p.join(',')).join(' '))\n      .attr('fill','none').attr('stroke','#2d7a4a').attr('stroke-width',2.8)\n      .attr('stroke-linejoin','round').attr('stroke-linecap','round').attr('opacity',0.95);\n  }\n  const upPts = [];\n  for(let i=currentIdx; i&lt;citiesList.length; i++){\n    const p = cityPt(citiesList[i]);\n    if(p &amp;&amp; (upPts.length===0 || upPts[upPts.length-1][0]!==p.x || upPts[upPts.length-1][1]!==p.y))\n      upPts.push([p.x, p.y]);\n  }\n  if(upPts.length&gt;1){\n    svg.append('polyline')\n      .attr('points', upPts.map(p=&gt;p.join(',')).join(' '))\n      .attr('fill','none').attr('stroke','rgba(255,160,60,0.55)').attr('stroke-width',2)\n      .attr('stroke-dasharray','7 5').attr('stroke-linecap','round').attr('opacity',0.9);\n  }\n  citiesList.forEach((c,i)=&gt;{\n    const p = cityPt(c);\n    if(!p) return;\n    const st = i&lt;currentIdx?'visited':i===currentIdx?'current':'upcoming';\n    const g = svg.append('g').attr('class','city-marker').attr('cursor','default');\n    if(st==='current'){\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',11).attr('fill','rgba(255,102,0,0.20)').attr('stroke','none');\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',7).attr('fill','#ff6600').attr('stroke','#fff').attr('stroke-width',2);\n    } else if(st==='visited'){\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',4).attr('fill','#2d7a4a').attr('stroke','#4CAF7D').attr('stroke-width',1.5);\n    } else {\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',3.5).attr('fill','#ff9933').attr('stroke','#fff').attr('stroke-width',1);\n    }\n    \/* \u2500\u2500 city name label \u2500\u2500 *\/\n    appendCityLabel(g, p.x, p.y, c.name, st, c._fromSheet||false);\n    g.on('mouseenter', (evt)=&gt;{\n      tooltip.innerHTML=`&lt;strong&gt;${c.name}&lt;\/strong&gt;&lt;br&gt;${c.dateStr}, 2026 \u00b7 Day ${c.day}`;\n      tooltip.style.opacity='1';\n    }).on('mousemove',(evt)=&gt;{\n      const wrap = svgEl.parentElement.getBoundingClientRect();\n      let tx = evt.clientX - wrap.left + 12;\n      let ty = evt.clientY - wrap.top - 10;\n      if(tx + 180 &gt; wrap.width) tx = tx - 190;\n      tooltip.style.left=tx+'px';tooltip.style.top=ty+'px';\n    }).on('mouseleave',()=&gt;{ tooltip.style.opacity='0'; });\n  });\n  if(extraPoints){\n    extraPoints.forEach(ep=&gt;{\n      const p = latLonToXY(proj, ep.lat, ep.lon);\n      if(!p) return;\n      svg.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',5)\n        .attr('fill',ep.color||'#e07030').attr('stroke','#fff').attr('stroke-width',1.5).attr('opacity',0.85);\n    });\n  }\n  if(svgId==='main-map-svg' &amp;&amp; citiesList[currentIdx]){\n    document.getElementById('map-badge-city').textContent = citiesList[currentIdx].name;\n  }\n}\n\n\/* \u2500\u2500 renderMainMapWithZoom \u2014 main live map with D3 zoom \u2500\u2500 *\/\nlet zoomBehavior = null;\nfunction renderMainMapWithZoom(){\n  const svgEl = document.getElementById('main-map-svg');\n  if(!svgEl) return;\n  const svg = d3.select('#main-map-svg');\n  svg.selectAll('*').remove();\n  const rect = svgEl.getBoundingClientRect();\n  const W = rect.width || svgEl.parentElement.clientWidth || 500;\n  const H = rect.height || svgEl.parentElement.clientHeight || 500;\n  svg.attr('viewBox',`0 0 ${W} ${H}`);\n  const proj = makeProjection(svgEl);\n  mainProjection = proj;\n  const pathGen = d3.geoPath().projection(proj);\n  const tooltip = document.getElementById('map-tooltip');\n  const root = svg.append('g').attr('id','zoom-root');\n  root.append('rect').attr('width',W).attr('height',H).attr('fill','#b8d4e8');\n  if (indiaGeoJSON &amp;&amp; indiaGeoJSON.features &amp;&amp; indiaGeoJSON.features.length) {\n    root.selectAll('.india-path')\n      .data(indiaGeoJSON.features)\n      .enter().append('path')\n      .attr('class','india-path')\n      .attr('d',pathGen)\n      .attr('fill','#d4ebd4')\n      .attr('stroke','#5a9a6a')\n      .attr('stroke-width', 1.0);\n  }\n  \/* \u2500\u2500 Background India cities layer \u2500\u2500 *\/\n  const yataCityNames = new Set(cities.map(c=&gt;c.name.toLowerCase()));\n  INDIA_BG_CITIES.forEach(bc=&gt;{\n    if(yataCityNames.has(bc.n.toLowerCase())) return; \/\/ skip if already on yatra route\n    const pt = proj([bc.lon, bc.lat]);\n    if(!pt) return;\n    const bx=pt[0], by=pt[1];\n    const bg = root.append('g').attr('pointer-events','none');\n    \/\/ dot\n    bg.append('circle').attr('cx',bx).attr('cy',by)\n      .attr('r', bc.cap ? 2 : 1.5)\n      .attr('fill', bc.cap ? '#aaa' : '#bbb')\n      .attr('stroke','rgba(255,255,255,0.6)')\n      .attr('stroke-width', 0.7);\n    \/\/ label\n    bg.append('text')\n      .attr('x', bx).attr('y', by - 3)\n      .attr('text-anchor','middle')\n      .attr('font-size', bc.cap ? 5.5 : 5)\n      .attr('font-weight', bc.cap ? '500' : '400')\n      .attr('font-family',\"'Outfit',sans-serif\")\n      .attr('fill', bc.cap ? 'rgba(80,80,80,0.75)' : 'rgba(110,110,110,0.6)')\n      .attr('paint-order','stroke')\n      .attr('stroke','rgba(255,255,255,0.8)')\n      .attr('stroke-width', 1.8)\n      .attr('stroke-linejoin','round')\n      .text(bc.n);\n  });\n  function cityPt(c){ const pt=proj([c.lon,c.lat]); return pt?{x:pt[0],y:pt[1]}:null; }\n  const donePts=[];\n  for(let i=0;i&lt;=cur;i++){\n    const p=cityPt(cities[i]);\n    if(p&amp;&amp;(donePts.length===0||donePts[donePts.length-1][0]!==p.x||donePts[donePts.length-1][1]!==p.y))\n      donePts.push([p.x,p.y]);\n  }\n  if(donePts.length&gt;1){\n    const doneLineEl = root.append('polyline')\n      .attr('points',donePts.map(p=&gt;p.join(',')).join(' '))\n      .attr('fill','none').attr('stroke','#1db954').attr('stroke-width',4)\n      .attr('stroke-linejoin','round').attr('stroke-linecap','round').attr('opacity',1);\n    let totalLen = 0;\n    for(let i=1;i&lt;donePts.length;i++){\n      const dx=donePts[i][0]-donePts[i-1][0], dy=donePts[i][1]-donePts[i-1][1];\n      totalLen += Math.sqrt(dx*dx+dy*dy);\n    }\n    doneLineEl.attr('stroke-dasharray', totalLen+' '+totalLen)\n      .attr('stroke-dashoffset', totalLen);\n    doneLineEl.transition().duration(1800).ease(d3.easeCubicInOut)\n      .attr('stroke-dashoffset', 0);\n  }\n  const upPts=[];\n  for(let i=cur;i&lt;cities.length;i++){\n    const p=cityPt(cities[i]);\n    if(p&amp;&amp;(upPts.length===0||upPts[upPts.length-1][0]!==p.x||upPts[upPts.length-1][1]!==p.y))\n      upPts.push([p.x,p.y]);\n  }\n  if(upPts.length&gt;1)\n    root.append('polyline').attr('points',upPts.map(p=&gt;p.join(',')).join(' '))\n      .attr('fill','none').attr('stroke','#ff8c00').attr('stroke-width',2.5)\n      .attr('stroke-dasharray','8 5').attr('stroke-linecap','round').attr('opacity',0.85);\n\n  cities.forEach((c,i)=&gt;{\n    const p=cityPt(c); if(!p) return;\n    const st=i&lt;cur?'visited':i===cur?'current':'upcoming';\n    const fromSheet = c._fromSheet || false;\n    const g=root.append('g').attr('cursor','default');\n    if(st==='current'){\n      const outerRing = g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',14)\n        .attr('fill','rgba(229,57,53,0.18)').attr('stroke','rgba(229,57,53,0.4)').attr('stroke-width',1.5);\n      function pulseRing(){\n        outerRing.transition().duration(900).attr('r',18).attr('opacity',0.1)\n          .transition().duration(900).attr('r',14).attr('opacity',1)\n          .on('end',pulseRing);\n      }\n      pulseRing();\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',7)\n        .attr('fill','#e53935').attr('stroke','#fff').attr('stroke-width',2.2);\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',2.5).attr('fill','#fff');\n    } else if(st==='visited'){\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',3.8).attr('fill','#27ae60').attr('stroke','#4CAF7D').attr('stroke-width',1.5);\n    } else {\n      g.append('circle').attr('cx',p.x).attr('cy',p.y).attr('r',3).attr('fill','#ff9933').attr('stroke','#fff').attr('stroke-width',1);\n    }\n    \/* \u2500\u2500 city name label on main live map \u2500\u2500 *\/\n    appendCityLabel(g, p.x, p.y, c.name, st, fromSheet);\n    g.append('rect').attr('x',p.x-12).attr('y',p.y-12).attr('width',24).attr('height',24).attr('fill','transparent')\n      .on('mouseenter',(evt)=&gt;{\n        tooltip.innerHTML=`&lt;strong&gt;${c.name}&lt;\/strong&gt;&lt;br&gt;${c.dateStr}, 2026 \u00b7 Day ${c.day}`;\n        tooltip.style.opacity='1';\n      })\n      .on('mousemove',(evt)=&gt;{\n        const wrap=svgEl.parentElement.getBoundingClientRect();\n        let tx=evt.clientX-wrap.left+12, ty=evt.clientY-wrap.top-10;\n        if(tx+180&gt;wrap.width) tx=tx-190;\n        tooltip.style.left=tx+'px'; tooltip.style.top=ty+'px';\n      })\n      .on('mouseleave',()=&gt;tooltip.style.opacity='0')\n      .on('click',()=&gt;{\n        if(!zoomBehavior) return;\n        const s=3.2;\n        d3.select('#main-map-svg').transition().duration(600).call(\n          zoomBehavior.transform,\n          d3.zoomIdentity.translate(W\/2,H\/2).scale(s).translate(-p.x,-p.y)\n        );\n      });\n  });\n\n  const cc=cities[cur];\n  if(cc){\n    document.getElementById('map-badge-city').textContent=cc.name;\n  }\n  if(!zoomBehavior){\n    zoomBehavior=d3.zoom().scaleExtent([0.7, 10]).on('zoom',(evt)=&gt;{\n      root.attr('transform',evt.transform);\n    });\n  } else {\n    zoomBehavior.on('zoom',(evt)=&gt;root.attr('transform',evt.transform));\n  }\n  svg.call(zoomBehavior);\n  svg.append('rect').attr('x',W-46).attr('y',10).attr('width',36).attr('height',70).attr('rx',8)\n    .attr('fill','rgba(10,40,20,0.75)').attr('stroke','rgba(255,255,255,0.2)').attr('stroke-width',1);\n  svg.append('text').attr('x',W-28).attr('y',34).attr('text-anchor','middle')\n    .attr('fill','#fff').attr('font-size',18).attr('font-family','sans-serif').attr('cursor','pointer')\n    .text('+').on('click',()=&gt;svg.transition().duration(300).call(zoomBehavior.scaleBy,1.5));\n  svg.append('line').attr('x1',W-44).attr('x2',W-12).attr('y1',45).attr('y2',45)\n    .attr('stroke','rgba(255,255,255,0.25)').attr('stroke-width',1);\n  svg.append('text').attr('x',W-28).attr('y',63).attr('text-anchor','middle')\n    .attr('fill','#fff').attr('font-size',18).attr('font-family','sans-serif').attr('cursor','pointer')\n    .text('\u2212').on('click',()=&gt;svg.transition().duration(300).call(zoomBehavior.scaleBy,0.67));\n}\n\nfunction renderDashMap(data){\n  const svgEl=document.getElementById('d-map-svg');if(!svgEl)return;\n  const today=todayISO();\n  const pts=[];\n  data.forEach(item=&gt;{\n    const iso=dNorm(item.Date);if(!iso)return;\n    const cn=(item.City||'').trim();if(!cn)return;\n    let la=parseFloat(item.Latitude),lo=parseFloat(item.Longitude);\n    if(isNaN(la)||isNaN(lo)){const gq=GQ_MAP[cn.toLowerCase()];if(!gq)return;la=gq.lat;lo=gq.lon;}\n    let color=iso&lt;today?'#aaa':iso===today?'#e53935':'#e07030';\n    pts.push({lat:la,lon:lo,name:cn,iso,color,current:iso===today});\n  });\n  renderD3Map('d-map-svg','d-map-tooltip',cities,cur,pts);\n}\nfunction haversineKm(a,b){\n  const R=6371,dLat=(b.lat-a.lat)*Math.PI\/180,dLon=(b.lon-a.lon)*Math.PI\/180;\n  const s=Math.sin(dLat\/2)**2+Math.cos(a.lat*Math.PI\/180)*Math.cos(b.lat*Math.PI\/180)*Math.sin(dLon\/2)**2;\n  return R*2*Math.atan2(Math.sqrt(s),Math.sqrt(1-s));\n}\nfunction updateSidebar(){\n  if(!cities.length)return;\n  const c=cities[cur],nxt=cur&lt;cities.length-1?cities[cur+1]:null;\n  const pct=Math.round((cur\/(cities.length-1))*100);\n  const daysDone=Math.max(0,c.day-1);\n  const daysLeft=Math.max(0,100-c.day+1);\n  \/\/ NAYA lagao:\nlet kmDone = 0;\nif (allYatraData &amp;&amp; allYatraData.length) {\n  const today = todayISO();\n  allYatraData.forEach(item =&gt; {\n    const iso = dNorm(item.Date);\n    if (!iso || iso &gt; today) return;\n    const km = parseFloat(String(item.KM || item.km || item['KM Covered'] || 0).replace(\/,\/g, ''));\n    if (!isNaN(km)) kmDone += km;\n  });\n} else {\n  \/\/ Fallback: haversine\n  for (let i = 0; i &lt; cur; i++)\n    kmDone += haversineKm(cities[i], cities[i+1]);\n}\nkmDone = Math.round(kmDone);\n  let peopleMet=0;\n  const today=todayISO();\n  if(allYatraData&amp;&amp;allYatraData.length){\n    allYatraData.forEach(item=&gt;{\n      const iso=dNorm(item.Date);if(!iso||iso&gt;today)return;\n      const keys=Object.keys(item);const pk=keys.find(k=&gt;\/people\/i.test(k));\n      if(pk){const n=parseInt(String(item[pk]||'0').replace(\/,\/g,''),10);if(!isNaN(n))peopleMet+=n;}\n    });\n  }\n  if(peopleMet===0&amp;&amp;window.statsData&amp;&amp;window.statsData.totalPeople) peopleMet=window.statsData.totalPeople;\n  document.getElementById('hdr-day').textContent=`Day ${c.day} of 100`;\n  document.getElementById('sb-city').textContent=c.isBreak?`${c.name} \u2014 Rest Day`:c.name;\n  document.getElementById('sb-date').textContent=`${c.dateStr}, 2026 \u00b7 Day ${c.day}`;\n  document.getElementById('day-pill').textContent=`Day ${c.day}`;\n  const badge=document.getElementById('live-badge');\n  if(c.isBreak){badge.classList.add('on-break');document.getElementById('live-txt').textContent='BREAK';}\n  else{badge.classList.remove('on-break');document.getElementById('live-txt').textContent='LIVE';}\n  if(nxt){document.getElementById('sb-next').textContent=nxt.name;document.getElementById('sb-next-when').textContent=nxt.dateStr+', 2026';}\n  else{document.getElementById('sb-next').textContent='Yatra Sampurna';document.getElementById('sb-next-when').textContent='\u2726 100 Days Complete \u2726';}\n  document.getElementById('prog-fill').style.width=Math.max(1,pct)+'%';\n  document.getElementById('prog-txt').textContent=pct+'% complete';\n  animateCounter('stat-done2',daysDone);animateCounter('stat-left2',daysLeft);\n  animateCounter('stat-people2',peopleMet);animateCounter('stat-km2',kmDone,' km');\n  setCircle('circ-done2',Math.round((daysDone\/100)*100));setCircle('circ-left2',Math.round((daysLeft\/100)*100));\n}\nfunction buildList(){\n  const list=document.getElementById('rlist');list.innerHTML='';\n  cities.forEach((c,i)=&gt;{\n    const st=i&lt;cur?'visited':i===cur?'current':'upcoming';\n    const item=document.createElement('div');item.className='ritem';\n    item.onclick=()=&gt;{\n      if(mainProjection &amp;&amp; zoomBehavior){\n        const pt=mainProjection([c.lon,c.lat]);\n        if(pt){\n          const svgEl=document.getElementById('main-map-svg');\n          const W=svgEl.getBoundingClientRect().width;\n          const H=svgEl.getBoundingClientRect().height;\n          d3.select('#main-map-svg').transition().duration(600).call(\n            zoomBehavior.transform,\n            d3.zoomIdentity.translate(W\/2,H\/2).scale(3.2).translate(-pt[0],-pt[1])\n          );\n        }\n      }\n    };\n    const dw=document.createElement('div');dw.className='rdot-wrap';\n    const dot=document.createElement('div');dot.className='rdot '+(c.isBreak&amp;&amp;st==='current'?'break':st);\n    dw.appendChild(dot);\n    if(i&lt;cities.length-1){const ln=document.createElement('div');ln.className='rconnect';dw.appendChild(ln);}\n    const nm=document.createElement('div');nm.className='rname '+st;nm.textContent=c.name;\n    if(st==='current'&amp;&amp;c.isBreak){const t=document.createElement('span');t.className='tag-break';t.textContent='BREAK';nm.appendChild(t);}\n    else if(st==='current'){const t=document.createElement('span');t.className='tag-live';t.textContent='LIVE';nm.appendChild(t);}\n    if(st==='upcoming'&amp;&amp;i===cur+1){const t=document.createElement('span');t.className='tag-next';t.textContent='NEXT';nm.appendChild(t);}\n    const info=document.createElement('div');info.style.flex='1';info.style.overflow='hidden';info.appendChild(nm);\n    const dt=document.createElement('div');dt.className='rdate';dt.textContent=c.dateStr;\n    item.appendChild(dw);item.appendChild(info);item.appendChild(dt);list.appendChild(item);\n  });\n  const items=list.querySelectorAll('.ritem');\n  if(items[cur])setTimeout(()=&gt;{const el=items[cur];const container=el.closest('.rlist');if(container){container.scrollTop=el.offsetTop-container.offsetTop-40;}},200);\n}\nfunction showCalEvtPopup(dateStr){\n  const nd=dNorm(dateStr);\n  const body=document.getElementById('cal-evt-body');\n  const title=document.getElementById('cal-evt-title');\n  const ev=allYatraData.find(item=&gt;dNorm(item.Date)===nd);\n  if(ev){\n    title.textContent=ev['Event Name']||ev.City||'Event Details';\n    body.innerHTML=`\n      &lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;City&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${ev.City||'N\/A'}&lt;\/div&gt;&lt;\/div&gt;\n      &lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Date&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${dFmt(ev.Date)}&lt;\/div&gt;&lt;\/div&gt;\n      ${ev['Event Name']?`&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Event&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${ev['Event Name']}&lt;\/div&gt;&lt;\/div&gt;`:''}\n      ${ev.Host?`&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Hosted By&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${ev.Host}&lt;\/div&gt;&lt;\/div&gt;`:''}\n      ${ev.Venue?`&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Venue&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${ev.Venue}&lt;\/div&gt;&lt;\/div&gt;`:''}\n      ${(ev.Time!==undefined&amp;&amp;ev.Time!==null&amp;&amp;ev.Time!=='')?`&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Time&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${fmtTime(ev.Time)}&lt;\/div&gt;&lt;\/div&gt;`:''}\n      ${ev['Short Description']?`&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Description&lt;\/span&gt;&lt;div class=\"cal-evt-val cal-evt-desc\"&gt;${ev['Short Description']}&lt;\/div&gt;&lt;\/div&gt;`:''}\n    `;\n  } else {\n    const dateObj=parseISO(nd),start=parseISO('2026-05-13'),end=parseISO('2026-08-20');\n    title.textContent=nd?dFmt(nd):'No Event';\n    if(dateObj&amp;&amp;start&amp;&amp;end&amp;&amp;dateObj&gt;=start&amp;&amp;dateObj&lt;=end){\n      const city=cities.find(c=&gt;c.iso===nd);\n      body.innerHTML=city\n        ?`&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Location&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;${city.name}&lt;\/div&gt;&lt;\/div&gt;&lt;div class=\"cal-evt-item\"&gt;&lt;span class=\"cal-evt-lbl\"&gt;Day&lt;\/span&gt;&lt;div class=\"cal-evt-val\"&gt;Day ${city.day} of 100&lt;\/div&gt;&lt;\/div&gt;&lt;div class=\"cal-evt-no-data\" style=\"padding-top:8px\"&gt;No specific event scheduled&lt;\/div&gt;`\n        :`&lt;div class=\"cal-evt-no-data\"&gt;No event scheduled for this date&lt;\/div&gt;`;\n    } else {\n      body.innerHTML=`&lt;div class=\"cal-evt-no-data\"&gt;No Yatra event on this date&lt;\/div&gt;`;\n    }\n  }\n  document.getElementById('cal-evt-overlay').classList.add('show');\n  \/\/ expand iframe to full viewport so fixed overlay covers everything\n  document.documentElement.style.height='100vh';\n  document.body.style.height='100vh';\n  document.body.style.overflow='hidden';\n  try{\n    var iframes=window.top.document.querySelectorAll('iframe');\n    iframes.forEach(function(f){\n      if(f.contentWindow===window){\n        f._origHeight=f._origHeight||f.style.height;\n        f._origPos=f._origPos||f.style.position;\n        f.style.cssText='height:'+window.top.innerHeight+'px !important;position:fixed !important;top:0 !important;left:0 !important;width:100% !important;z-index:99999 !important;margin:0 !important;';\n      }\n    });\n  }catch(e){}\n}\nfunction closeCalEvt(){\n  document.getElementById('cal-evt-overlay').classList.remove('show');\n  document.documentElement.style.height='';\n  document.body.style.height='';\n  document.body.style.overflow='';\n  try{\n    var iframes=window.top.document.querySelectorAll('iframe');\n    iframes.forEach(function(f){\n      if(f.contentWindow===window){\n        f.style.cssText='';\n        if(f._origHeight) f.style.height=f._origHeight;\n      }\n    });\n  }catch(e){}\n}\ndocument.addEventListener('keydown',e=&gt;{\n  if(e.key==='Escape'){closeCalEvt();closeDash();document.getElementById('india-lb').style.display='none';}\n});\n\/* \u2500\u2500 Shared calendar event builder \u2014 used by both calendars \u2500\u2500 *\/\nfunction buildCalEvents(data){\n  const today=todayISO();\n  const evts=[];\n  data.forEach(item=&gt;{\n    const iso=dNorm(item.Date);if(!iso)return;\n    const city=(item.City||'').trim();if(!city||city.toLowerCase()==='break')return;\n    const eventName=(item['Event Name']||'').trim();\n    const label=eventName?`${city} \u2013 ${eventName}`:city;\n    let color=iso&lt;today?'#888':iso===today?'#e53935':'#e07030';\n    evts.push({title:label,start:iso,color,allDay:true,\n      extendedProps:{dateStr:iso}});\n  });\n  return evts;\n}\n\nfunction initInlineCal(){\n  const el=document.getElementById('inline-calendar');\n  inlineCal=new FullCalendar.Calendar(el,{\n    initialView:'dayGridMonth',\n    headerToolbar:{left:'prev,next today',center:'title',right:''},\n    height:'auto',\n    themeSystem:'standard',\n    eventDisplay:'block',\n    eventMaxStack:3,\n    dayMaxEvents:3,\n    eventDidMount:function(info){\n      info.el.style.fontSize='9px';\n      info.el.style.padding='1px 3px';\n      info.el.style.borderRadius='3px';\n      info.el.style.cursor='pointer';\n    },\n    dateClick:info=&gt;showCalEvtPopup(info.dateStr),\n    eventClick:info=&gt;{\n      const ds=info.event.extendedProps.dateStr||info.event.startStr||(info.event.start?info.event.start.toISOString().split('T')[0]:'');\n      if(ds) showCalEvtPopup(ds);\n    }\n  });\n  inlineCal.render();\n}\n\nfunction updateInlineCal(data){\n  if(!inlineCal)return;\n  inlineCal.removeAllEvents();\n  inlineCal.addEventSource(buildCalEvents(data));\n}\nfunction fmtTime(v){\n  if(v===undefined||v===null||v==='')return'\u2014';\n  const s=String(v).trim();\n  if(s===''||s==='0'||s.toLowerCase()==='false'||s==='\u2014')return'\u2014';\n  \/\/ 1899-12-30 = Google Sheets empty time cell (Excel zero date)\n  if(s.startsWith('1899')||s.startsWith('1900-01-0'))return'\u2014';\n\n  \/\/ Apps Script sends Date as \"yyyy-MM-dd\" \u2014 if it's a full date with no time, skip\n  \/\/ But if Apps Script sends time as \"1899-12-30 HH:mm:ss\" extract time part\n  const spaceMatch=s.match(\/\\d{4}-\\d{2}-\\d{2}\\s+(\\d{1,2}):(\\d{2})\/);\n  if(spaceMatch){\n    const h=parseInt(spaceMatch[1],10),m=parseInt(spaceMatch[2],10);\n    if(h===0&amp;&amp;m===0)return'\u2014';\n    const ampm=h&gt;=12?'PM':'AM',hh=h%12===0?12:h%12;\n    return hh+':'+String(m).padStart(2,'0')+' '+ampm;\n  }\n\n  \/\/ Decimal fraction: Google Sheets internal time (0.375 = 9:00 AM)\n  const num=parseFloat(s);\n  if(!isNaN(num)&amp;&amp;num&gt;0&amp;&amp;num&lt;1){\n    const totalMin=Math.round(num*1440);\n    const h=Math.floor(totalMin\/60),m=totalMin%60;\n    const ampm=h&gt;=12?'PM':'AM',hh=h%12===0?12:h%12;\n    return hh+':'+String(m).padStart(2,'0')+' '+ampm;\n  }\n\n  \/\/ ISO datetime with T (e.g. \"1899-12-30T09:00:00.000Z\")\n  if(s.includes('T')){\n    const tp=s.split('T')[1];\n    if(tp){\n      const tm=tp.match(\/^(\\d{1,2}):(\\d{2})\/);\n      if(tm){\n        const h=parseInt(tm[1],10),m=parseInt(tm[2],10);\n        if(h===0&amp;&amp;m===0)return'\u2014';\n        const ampm=h&gt;=12?'PM':'AM',hh=h%12===0?12:h%12;\n        return hh+':'+String(m).padStart(2,'0')+' '+ampm;\n      }\n    }\n    return'\u2014';\n  }\n\n  \/\/ Plain HH:MM or HH:MM:SS with optional AM\/PM\n  const match=s.match(\/^(\\d{1,2}):(\\d{2})(?::\\d{2})?(\\s*(AM|PM))?$\/i);\n  if(match){\n    let h=parseInt(match[1],10);const m=parseInt(match[2],10);\n    const period=(match[4]||'').toUpperCase();\n    if(h===0&amp;&amp;m===0&amp;&amp;!period)return'\u2014';\n    if(period==='PM'&amp;&amp;h!==12)h+=12;\n    else if(period==='AM'&amp;&amp;h===12)h=0;\n    const ampm=h&gt;=12?'PM':'AM',hh=h%12===0?12:h%12;\n    return hh+':'+String(m).padStart(2,'0')+' '+ampm;\n  }\n\n  \/\/ Already readable like \"10:00 AM\"\n  if(\/\\d.*[AaPp][Mm]\/.test(s))return s;\n  return'\u2014';\n}\nfunction render(){\n  renderMainMapWithZoom();\n  updateSidebar();\n  buildList();\n}\nconst REFRESH=5;\nlet dCalendar=null,dashInited=false;\nfunction expandIframe(){\n  document.documentElement.style.height='100vh';\n  document.body.style.height='100vh';\n  document.body.style.overflow='hidden';\n  try{\n    var iframes=window.top.document.querySelectorAll('iframe');\n    iframes.forEach(function(f){\n      if(f.contentWindow===window){\n        f._origHeight=f._origHeight||f.style.height;\n        f._origPos=f._origPos||f.style.position;\n        f.style.cssText='height:'+window.top.innerHeight+'px !important;position:fixed !important;top:0 !important;left:0 !important;width:100% !important;z-index:99999 !important;margin:0 !important;';\n      }\n    });\n  }catch(e){}\n}\nfunction restoreIframe(){\n  document.documentElement.style.height='';\n  document.body.style.height='';\n  document.body.style.overflow='';\n  try{\n    var iframes=window.top.document.querySelectorAll('iframe');\n    iframes.forEach(function(f){\n      if(f.contentWindow===window){\n        f.style.cssText='';\n        if(f._origHeight) f.style.height=f._origHeight;\n      }\n    });\n  }catch(e){}\n}\nfunction showCalendar(){\n  document.getElementById('dash-overlay').classList.add('show');\n  expandIframe();\n  if(!dashInited){dashInited=true;setTimeout(initDash,80);}\n  else renderDashMap(allYatraData);\n}\nfunction closeDash(){document.getElementById('dash-overlay').classList.remove('show');closeDEvt();restoreIframe();}\nfunction closeDEvt(){document.getElementById('d-evt-modal').classList.remove('show');}\nfunction initDash(){\n  renderDashMap(allYatraData);\n  const calEl=document.getElementById('d-calendar');\n  dCalendar=new FullCalendar.Calendar(calEl,{\n    initialView:'dayGridMonth',\n    headerToolbar:{left:'prev,next today',center:'title',right:'dayGridMonth'},\n    height:'auto',\n    contentHeight:'auto',\n    themeSystem:'standard',\n    eventDisplay:'block',\n    eventMaxStack:3,\n    dayMaxEvents:3,\n    eventDidMount:function(info){\n      info.el.style.fontSize='9px';\n      info.el.style.padding='1px 3px';\n      info.el.style.borderRadius='3px';\n      info.el.style.cursor='pointer';\n    },\n    dateClick:info=&gt;showCalEvtPopup(info.dateStr),\n    eventClick:info=&gt;{\n      const ds=info.event.extendedProps.dateStr||info.event.startStr||(info.event.start?info.event.start.toISOString().split('T')[0]:'');\n      if(ds) showCalEvtPopup(ds);\n    }\n  });\n  dCalendar.render();\n  updateDashUI(allYatraData);\n  setInterval(fetchDashData,REFRESH*60*1000);\n}\nasync function fetchDashData(){\n  try{\n    const res=await fetch(`${API_URL}?t=${Date.now()}`);\n    const result=await res.json();\n    if(result.status==='success'){\n      allYatraData=result.data;\n      \/\/ Debug: log first item's Time field to console\n      if(result.data&amp;&amp;result.data[0]) console.log('[TIME DEBUG]',JSON.stringify(result.data[0]));\n      if(typeof result.totalPeople==='number'&amp;&amp;result.totalPeople&gt;0){\n        window.statsData={totalPeople:result.totalPeople,rows:result.stats||[]};\n      } else if(result.stats&amp;&amp;Array.isArray(result.stats)){\n        const total=result.stats.reduce((sum,row)=&gt;{\n          const keys=Object.keys(row);const pk=keys.find(k=&gt;\/people\\s*met|peoplemet|people_met|count\/i.test(k));\n          const n=pk?parseInt(String(row[pk]||'0').replace(\/,\/g,''),10):0;return sum+(isNaN(n)?0:n);\n        },0);\n        window.statsData={totalPeople:total,rows:result.stats};\n      }\n      const sc=buildCitiesFromSheet(allYatraData);\n      if(sc&amp;&amp;sc.length){cities=sc;cur=getCurrentIndex(cities);render();}\n      else render();\n      updateInlineCal(allYatraData);\n      if(dashInited)updateDashUI(allYatraData);\n    }\n  }catch(e){console.warn('Sheet fetch failed, using GQ fallback:',e);}\n}\nfunction updateDashUI(data){\n  if(!dCalendar)return;\n  const today=todayISO();\n  dCalendar.removeAllEvents();\n  dCalendar.addEventSource(buildCalEvents(data));\n  \/\/ Update current city banner\n  const ce=data.find(item=&gt;dNorm(item.Date)===today);\n  const banner=document.getElementById('d-current-city-text');\n  if(ce){banner.textContent=`${ce.City||''} (${ce['Event Name']||''})`;banner.style.color='#e53935';}\n  else{banner.textContent='No event scheduled for today.';banner.style.color='';}\n  renderDashMap(data);\n}\nlet resizeTimer;\nfunction onResize(){\n  clearTimeout(resizeTimer);\n  resizeTimer=setTimeout(()=&gt;{\n    if(cities.length) renderMainMapWithZoom();\n    if(dashInited) renderDashMap(allYatraData);\n  },250);\n}\nwindow.addEventListener('resize', onResize);\nwindow.addEventListener('orientationchange', onResize);\nif(window.visualViewport){\n  window.visualViewport.addEventListener('resize', onResize);\n}\nasync function init(){\n  cities=buildCitiesFromGQ();cur=getCurrentIndex(cities);\n  initInlineCal();\n  await loadIndiaGeoJSON();\n  render();\n  await fetchDashData();\n}\ninit();\n\n\/\/ This is a new code \njQuery(document).ready(function($) {\n    setTimeout(function() {\n        if ($('#tcb_landing_page').length) {\n            $('html, body').animate({\n                scrollTop: $('#tcb_landing_page').offset().top\n            }, 800);\n        }\n    }, 1000); \/\/ 2000ms = 1 seconds\n});\njQuery(function($) {\n    $('#yatra-invite').click(function(e) {\n        e.preventDefault();\n\n        var target = $('#take-action-invite-yatra-now');\n\n        if (target.length) {\n            $('html, body').stop().animate({\n                scrollTop: target.offset().top\n            }, 800);\n        }\n    });\n});0\n[\/tcb-script]<\/code><\/div>","tve_custom_css":"@media (min-width: 300px){[data-css=\"tve-u-69e5dd6367aff1\"] { --tve-alignment: center; float: none; margin-right: 16px !important; margin-left: 19px !important; padding-left: 0px !important; }}@media (max-width: 767px){[data-css=\"tve-u-69e5dd6367aff1\"] { --tve-alignment: center; float: none; margin-right: 297px !important; padding-right: 87px !important; margin-left: 30px !important; margin-bottom: 14px !important; padding-left: 349px !important; }}","tve_user_custom_css":"","tve_globals":{"e":"1","font_cls":[]},"tcb2_ready":1,"tcb_editor_enabled":1,"tve_landing_page":"","_tve_header":"","_tve_footer":""},"class_list":["post-1333","page","type-page","status-publish","hentry","post-wrapper","thrv_wrapper"],"_links":{"self":[{"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/pages\/1333","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/comments?post=1333"}],"version-history":[{"count":123,"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/pages\/1333\/revisions"}],"predecessor-version":[{"id":1670,"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/pages\/1333\/revisions\/1670"}],"wp:attachment":[{"href":"https:\/\/thefiniteearth.org\/hindi\/wp-json\/wp\/v2\/media?parent=1333"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}