Widget:TwinSuns: Difference between revisions

From WyrdeWiki
No edit summary
No edit summary
Line 50: Line 50:
   </div>
   </div>


   <!-- date line with extra top margin to avoid cosine overlap -->
   <!-- date line moved slightly lower to avoid cosine overlap -->
   <div style="margin:.65rem 0 .35rem 0;">
   <div style="margin:.85rem 0 .4rem 0;">
     <strong>Date:</strong>
     <strong>Date:</strong>
     <span id="<!--{$id|default:'ts'|escape:'html'}-->-date">Fortnight of Renewal (Dawning), day 8 (FR 8)</span>
     <span id="<!--{$id|default:'ts'|escape:'html'}-->-date">Fortnight of Renewal (Dawning), day 8 (FR 8)</span>
Line 103: Line 103:
   };
   };


   // sizes: keep suns proportionally similar to your PNGs
   // slightly larger stars (still proportional).  **Only small change.**
   function setStarSizes(){
   function setStarSizes(){
     var w = el.stage.clientWidth;
     var w = el.stage.clientWidth;
     var base = Math.round(w * 0.05);     // tweakable
     var base = Math.round(w * 0.075);             // was 0.05
     el.s.width = base; el.s.height = base;
     el.s.width = base; el.s.height = base;
     el.v.width = Math.round(base * 0.72);
     el.v.width = Math.round(base * 0.72);
Line 116: Line 116:
   // helpers
   // helpers
   var TAU = Math.PI * 2;
   var TAU = Math.PI * 2;
   function cosPhase(d){ return Math.cos(TAU * ( (d-1) / 479 )); } // day1 => +1.0
  function phase(d){ return (d-1)/479; }                          // 0..~1
   function cosPhase(d){ return Math.cos(TAU * phase(d)); }       // day 1 -> +1
  function sinPhase(d){ return Math.sin(TAU * phase(d)); }
   function fmtDeg(x){ var s = (x>=0?"+":""); return s + x.toFixed(2) + "°"; }
   function fmtDeg(x){ var s = (x>=0?"+":""); return s + x.toFixed(2) + "°"; }
   function openingClosing(val, phase){ // val is Δ(d); dφ/dt sign decides
 
     // derivative of cos is -sin; positive means decreasing (Closing), negative means Opening
   // Opening/Closing per your definition:
     var s = Math.sin(TAU * ((phase))); // phase=(d-1)/479
  // Opening  : 0 -> ±Δ  (moving away from 0) => delta * delta' > 0
     return ( -s > 0 ? "Closing" : "Opening" );
  // Closing  : ±Δ -> 0  (moving toward 0)    => delta * delta' <= 0
  function openingClosing(d){
     var delta  = WOBBLE * cosPhase(d);
     var d_delta = -WOBBLE * TAU * sinPhase(d); // derivative of Δ(t)
     return (delta * d_delta > 0) ? "Opening" : "Closing";
   }
   }


Line 140: Line 146:
   }
   }


   // layout constants
   // split wobble shares (kept as before)
   var SOL_SHARE = 1.0, VAE_SHARE = 1.5; // sum = Δ split
   var SOL_SHARE = 1.0, VAE_SHARE = 1.5;
   var SUM = SOL_SHARE + VAE_SHARE;
   var SUM = SOL_SHARE + VAE_SHARE;


   function update(){
   function update(){
     var d = parseInt(el.rng.value,10);
     var d = parseInt(el.rng.value,10);
    var phase = (d-1)/479;


     // angles (deg)
     // angles (deg)
     var delta = WOBBLE * cosPhase(d);        // +Δ at day 1
     var delta = WOBBLE * cosPhase(d);        // +Δ at day 1
     var eq = -EQUATOR * cosPhase(d);         // lowest (negative) at day 1, highest midsummer
     var eq   = -EQUATOR * cosPhase(d);     // lowest at day 1, highest midsummer


     el.day.textContent = d + " / 479";
     el.day.textContent = d + " / 479";
     el.date.textContent = dateText(d);
     el.date.textContent = dateText(d);


    var oc = openingClosing(delta, phase);
     el.rel.textContent = fmtDeg(delta) + " (" + openingClosing(d) + ")";
     el.rel.textContent = fmtDeg(delta) + " (" + oc + ")";
     el.eq.textContent  = fmtDeg(eq);
     el.eq.textContent  = fmtDeg(eq);


Line 163: Line 167:
     var h = el.stage.clientHeight;
     var h = el.stage.clientHeight;
     var cx = w * 0.5;
     var cx = w * 0.5;
     var cy = h * 0.33;  // place suns in upper third
     var cy = h * 0.33;  // upper third


     // horizontal visual cue: center pair around cx with SEP/2 offset
     // horizontal visual cue: center pair around cx with SEP/2 offset
     var dx = (SEP/2) * DEGPX; // pixels
     var dx = (SEP/2) * DEGPX; // pixels


     // vertical:
     // vertical: barycenter seasonal tilt (eq) + opposite wobble offsets
    // barycenter seasonal tilt (eq) plus split wobble offsets
     var solOff =  (delta * (SOL_SHARE/SUM)) * DEGPX;
     var solOff =  (delta * (SOL_SHARE/SUM)) * DEGPX;   // Solara goes positive with +Δ
     var vaeOff = -(delta * (VAE_SHARE/SUM)) * DEGPX;
     var vaeOff = -(delta * (VAE_SHARE/SUM)) * DEGPX;   // Vaelus opposite
     var yBase = cy - (eq * DEGPX);
 
     var yBase = cy - (eq * DEGPX);


     // place
     // place
Line 190: Line 192:
     update();
     update();
   }
   }
   el.rng.addEventListener("input", function(){
   el.rng.addEventListener("input", update);
    // keep cosine image width exactly matching slider—nothing to do here, width is CSS-bound
    update();
  });
   el.play.addEventListener("click", function(){
   el.play.addEventListener("click", function(){
     if(!playing){
     if(!playing){

Revision as of 20:43, 11 November 2025

This widget shows WyrdeHaven’s twin suns with seasonal wobble & calendar.

Usage

1 / 479
Date: Fortnight of Renewal (Dawning), day 8 (FR 8)
Sky Solara Vaelus
Relative Solar Inclination (Δ): +2.50° (Closing)
Seasonal Equatorial Inclination (barycenter): -8.00°

param meaning default
size max stage width (px) 768
fps play speed (frames/s) 5
wobble solar relative wobble amplitude (Δ, degrees) 2.5
equator seasonal/barycenter max tilt (degrees) 8
sep visible horizontal separation between suns (degrees) 2.5
degpx vertical degree→pixel scale (px per degree) 10