@eaprelsky/nocturna-wheel 3.0.1 → 3.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -287,7 +287,7 @@ class IconProvider {
287
287
  /**
288
288
  * IconData.js
289
289
  * Auto-generated module containing inline SVG icons as data URLs
290
- * Generated at: 2025-11-14T10:26:57.036Z
290
+ * Generated at: 2025-11-16T11:33:48.632Z
291
291
  *
292
292
  * This file is automatically generated by the build process.
293
293
  * Do not edit manually - changes will be overwritten.
@@ -1986,10 +1986,21 @@ class ZodiacRenderer extends BaseRenderer {
1986
1986
  ];
1987
1987
 
1988
1988
  circles.forEach(circleData => {
1989
+ // Determine stroke color and width based on circle type
1990
+ let strokeColor = "#999";
1991
+ let strokeWidth = "0.5";
1992
+ if (circleData.class === "chart-outer-circle") {
1993
+ strokeColor = "#666";
1994
+ strokeWidth = "1";
1995
+ }
1996
+
1989
1997
  const circle = this.svgUtils.createSVGElement("circle", {
1990
1998
  cx: this.centerX,
1991
1999
  cy: this.centerY,
1992
2000
  r: circleData.r,
2001
+ fill: "transparent", // Explicitly set transparent fill to avoid default black
2002
+ stroke: strokeColor, // Explicitly set stroke to ensure visibility
2003
+ "stroke-width": strokeWidth, // Explicitly set stroke width
1993
2004
  class: `zodiac-element ${circleData.class}` // Add base class
1994
2005
  });
1995
2006
  parentGroup.appendChild(circle);
@@ -2024,6 +2035,8 @@ class ZodiacRenderer extends BaseRenderer {
2024
2035
  y1: point1.y,
2025
2036
  x2: point2.x,
2026
2037
  y2: point2.y,
2038
+ stroke: "#999", // Explicitly set stroke to ensure visibility
2039
+ "stroke-width": "0.75", // Explicitly set stroke width
2027
2040
  class: `zodiac-element zodiac-division-line ${specialClass}`
2028
2041
  });
2029
2042
 
@@ -2215,12 +2228,34 @@ class HouseRenderer extends BaseRenderer {
2215
2228
  const innerPoint = this.svgUtils.pointOnCircle(this.centerX, this.centerY, this.innerRadius, angle);
2216
2229
  const middlePoint = this.svgUtils.pointOnCircle(this.centerX, this.centerY, this.middleRadius, angle);
2217
2230
 
2231
+ // Determine stroke color and width based on line type
2232
+ let innerStrokeColor = "#999";
2233
+ let innerStrokeWidth = "0.75";
2234
+
2235
+ let outerStrokeColor = "#999";
2236
+ let outerStrokeWidth = "0.75";
2237
+ let outerStrokeDasharray = null;
2238
+
2239
+ if (axisClass.includes('axis')) {
2240
+ // Cardinal points (ASC, DSC, IC, MC) - solid, darker
2241
+ innerStrokeColor = "#555";
2242
+ innerStrokeWidth = "1";
2243
+ outerStrokeColor = "#555";
2244
+ outerStrokeWidth = "1";
2245
+ // Axes are always solid
2246
+ } else {
2247
+ // Regular lines - outer lines are dashed
2248
+ outerStrokeDasharray = "2,2";
2249
+ }
2250
+
2218
2251
  // Create line from inner to middle circle
2219
2252
  const innerLine = this.svgUtils.createSVGElement("line", {
2220
2253
  x1: innerPoint.x,
2221
2254
  y1: innerPoint.y,
2222
2255
  x2: middlePoint.x,
2223
2256
  y2: middlePoint.y,
2257
+ stroke: innerStrokeColor, // Explicitly set stroke to ensure visibility
2258
+ "stroke-width": innerStrokeWidth, // Explicitly set stroke width
2224
2259
  class: `house-element house-division-line ${axisClass}`
2225
2260
  });
2226
2261
 
@@ -2242,13 +2277,21 @@ class HouseRenderer extends BaseRenderer {
2242
2277
  const extendedPoint = this.svgUtils.pointOnCircle(this.centerX, this.centerY, this.extendedRadius, angle);
2243
2278
 
2244
2279
  // Create line from outer circle to extended point
2245
- const outerLine = this.svgUtils.createSVGElement("line", {
2280
+ const outerLineAttrs = {
2246
2281
  x1: outerPoint.x,
2247
2282
  y1: outerPoint.y,
2248
2283
  x2: extendedPoint.x,
2249
2284
  y2: extendedPoint.y,
2285
+ stroke: outerStrokeColor, // Explicitly set stroke to ensure visibility
2286
+ "stroke-width": outerStrokeWidth, // Explicitly set stroke width
2250
2287
  class: `house-element house-division-line outer ${axisClass}`
2251
- });
2288
+ };
2289
+
2290
+ if (outerStrokeDasharray) {
2291
+ outerLineAttrs["stroke-dasharray"] = outerStrokeDasharray;
2292
+ }
2293
+
2294
+ const outerLine = this.svgUtils.createSVGElement("line", outerLineAttrs);
2252
2295
 
2253
2296
  // Ensure cardinal points render above zodiac lines
2254
2297
  if (axisClass.includes('axis')) {
@@ -2451,6 +2494,8 @@ class BasePlanetRenderer extends BaseRenderer {
2451
2494
  isPrimary: planetType === 'primary',
2452
2495
  type: planetType,
2453
2496
  color: p.color || '#000000',
2497
+ // Retrograde flag - whether the planet is retrograde
2498
+ retrograde: p.retrograde === true,
2454
2499
  // Track which radius this planet is being rendered at
2455
2500
  dotRadius: dotRadius,
2456
2501
  iconRadius: iconRadius
@@ -2559,6 +2604,50 @@ class PlanetSymbolRenderer extends BasePlanetRenderer {
2559
2604
  return icon;
2560
2605
  }
2561
2606
 
2607
+ /**
2608
+ * Renders a retrograde indicator (small "R" symbol) in the bottom-right corner of the planet icon
2609
+ * @param {Element} parentGroup - The parent SVG group
2610
+ * @param {Object} planet - Planet object with calculated positions
2611
+ * @param {number} iconSize - Size of the icon in pixels
2612
+ * @returns {Element} - The created retrograde indicator element
2613
+ */
2614
+ renderRetrogradeIndicator(parentGroup, planet, iconSize = 24) {
2615
+ // Calculate position for "R" symbol in bottom-right corner of icon
2616
+ // Offset from icon center to bottom-right corner
2617
+ const offsetX = iconSize / 2 - 2; // Small offset from edge (2px from right edge)
2618
+ const offsetY = iconSize / 2 - 2; // Small offset from bottom edge
2619
+
2620
+ // Position relative to adjusted icon center
2621
+ const rX = planet.adjustedIconX + offsetX;
2622
+ const rY = planet.adjustedIconY + offsetY;
2623
+
2624
+ // Get planet type for CSS classes
2625
+ const typeClass = planet.isPrimary ? 'primary' : 'secondary';
2626
+
2627
+ // Use planet color, but ensure visibility with darker shade if color is too light
2628
+ const planetColor = planet.color || '#000000';
2629
+
2630
+ // Create small "R" text element
2631
+ const retrogradeText = this.svgUtils.createSVGElement("text", {
2632
+ x: rX,
2633
+ y: rY,
2634
+ 'text-anchor': 'end',
2635
+ 'dominant-baseline': 'alphabetic',
2636
+ 'font-size': `${Math.max(7, iconSize * 0.3)}px`, // Scale with icon size, minimum 7px
2637
+ 'font-weight': 'bold',
2638
+ 'font-family': 'Arial, sans-serif',
2639
+ class: `planet-retrograde planet-${planet.name}-retrograde planet-${typeClass}-retrograde`,
2640
+ fill: planetColor,
2641
+ 'stroke': '#ffffff', // White stroke for better visibility
2642
+ 'stroke-width': '0.5',
2643
+ 'paint-order': 'stroke fill'
2644
+ });
2645
+
2646
+ retrogradeText.textContent = 'R';
2647
+
2648
+ return retrogradeText;
2649
+ }
2650
+
2562
2651
  /**
2563
2652
  * Renders a dot to mark the exact planet position
2564
2653
  * @param {Element} parentGroup - The parent SVG group
@@ -3118,6 +3207,12 @@ class PrimaryPlanetRenderer extends BasePlanetRenderer {
3118
3207
  const icon = this.symbolRenderer.renderPlanetSymbol(planetGroup, planet, iconSize);
3119
3208
  planetGroup.appendChild(icon);
3120
3209
 
3210
+ // Add retrograde indicator if planet is retrograde
3211
+ if (planet.retrograde) {
3212
+ const retrogradeIndicator = this.symbolRenderer.renderRetrogradeIndicator(planetGroup, planet, iconSize);
3213
+ planetGroup.appendChild(retrogradeIndicator);
3214
+ }
3215
+
3121
3216
  // Add tooltip
3122
3217
  this.symbolRenderer.addPlanetTooltip(planetGroup, planet);
3123
3218
 
@@ -3293,6 +3388,12 @@ class SecondaryPlanetRenderer extends BasePlanetRenderer {
3293
3388
  const icon = this.symbolRenderer.renderPlanetSymbol(planetGroup, planet, iconSize);
3294
3389
  planetGroup.appendChild(icon);
3295
3390
 
3391
+ // Add retrograde indicator if planet is retrograde
3392
+ if (planet.retrograde) {
3393
+ const retrogradeIndicator = this.symbolRenderer.renderRetrogradeIndicator(planetGroup, planet, iconSize);
3394
+ planetGroup.appendChild(retrogradeIndicator);
3395
+ }
3396
+
3296
3397
  // Add tooltip
3297
3398
  this.symbolRenderer.addPlanetTooltip(planetGroup, planet);
3298
3399
 
@@ -4941,7 +5042,8 @@ class NocturnaWheel {
4941
5042
  .map(([name, data]) => ({
4942
5043
  name: name,
4943
5044
  position: data.lon,
4944
- color: data.color || '#000000'
5045
+ color: data.color || '#000000',
5046
+ retrograde: !!data.retrograde
4945
5047
  }));
4946
5048
  primaryPlanetsWithCoords = this.renderers.planet.primaryRenderer.render(primaryGroup, primaryArray, 0, {
4947
5049
  config: this.config
@@ -4956,14 +5058,14 @@ class NocturnaWheel {
4956
5058
  .map(([name, data]) => ({
4957
5059
  name: name,
4958
5060
  position: data.lon,
4959
- color: data.color || '#000000'
5061
+ color: data.color || '#000000',
5062
+ retrograde: !!data.retrograde
4960
5063
  }));
4961
5064
  secondaryPlanetsWithCoords = this.renderers.planet.secondaryRenderer.render(secondaryGroup, secondaryArray, 0, {
4962
5065
  config: this.config
4963
5066
  });
4964
5067
  }
4965
5068
 
4966
- console.log(`NocturnaWheel: Rendered ${primaryPlanetsWithCoords.length} primary planets and ${secondaryPlanetsWithCoords.length} secondary planets`);
4967
5069
  }
4968
5070
 
4969
5071
  // Render three independent aspect types
@@ -4972,14 +5074,12 @@ class NocturnaWheel {
4972
5074
  if (this.config.primaryAspectSettings.enabled && primaryPlanetsWithCoords.length >= 2) {
4973
5075
  const primaryAspectsGroup = this.svgManager.getGroup('primaryAspects');
4974
5076
  this.renderers.aspect.render(primaryAspectsGroup, primaryPlanetsWithCoords, this.config.primaryAspectSettings);
4975
- console.log("NocturnaWheel: Rendered primary aspects");
4976
5077
  }
4977
5078
 
4978
5079
  // 2. Secondary aspects (inner circle to inner circle)
4979
5080
  if (this.config.secondaryAspectSettings.enabled && secondaryPlanetsWithCoords.length >= 2) {
4980
5081
  const secondaryAspectsGroup = this.svgManager.getGroup('secondaryAspects');
4981
5082
  this.renderers.aspect.render(secondaryAspectsGroup, secondaryPlanetsWithCoords, this.config.secondaryAspectSettings);
4982
- console.log("NocturnaWheel: Rendered secondary aspects");
4983
5083
  }
4984
5084
 
4985
5085
  // 3. Synastry aspects (outer circle to inner circle)
@@ -4993,10 +5093,8 @@ class NocturnaWheel {
4993
5093
  secondaryPlanetsWithCoords,
4994
5094
  this.config.synastryAspectSettings
4995
5095
  );
4996
- console.log("NocturnaWheel: Rendered synastry aspects");
4997
5096
  }
4998
5097
 
4999
- console.log("NocturnaWheel: Chart rendered");
5000
5098
  return this;
5001
5099
  }
5002
5100
 
@@ -5133,8 +5231,18 @@ class NocturnaWheel {
5133
5231
  // Update internal planets data
5134
5232
  // Ensure it matches the format expected internally (object)
5135
5233
  if (typeof data.planets === 'object' && !Array.isArray(data.planets)) {
5136
- this.planets = { ...this.planets, ...data.planets };
5137
- console.log("NocturnaWheel: Updated planets data.");
5234
+ // Perform a deep merge for each planet
5235
+ for (const planetName in data.planets) {
5236
+ if (this.planets[planetName]) {
5237
+ this.planets[planetName] = { ...this.planets[planetName], ...data.planets[planetName] };
5238
+ } else {
5239
+ this.planets[planetName] = data.planets[planetName];
5240
+ }
5241
+ }
5242
+ // Log retrograde flags specifically
5243
+ Object.keys(this.planets).forEach(key => {
5244
+ // console.log(` ${key}: retrograde = ${this.planets[key].retrograde}`);
5245
+ });
5138
5246
  } else {
5139
5247
  console.warn("NocturnaWheel.updateData: Invalid planets data format. Expected object.");
5140
5248
  }
@@ -5142,8 +5250,15 @@ class NocturnaWheel {
5142
5250
  if (data.secondaryPlanets) {
5143
5251
  // Update internal secondary planets data
5144
5252
  if (typeof data.secondaryPlanets === 'object' && !Array.isArray(data.secondaryPlanets)) {
5145
- this.secondaryPlanets = { ...this.secondaryPlanets, ...data.secondaryPlanets };
5146
- console.log("NocturnaWheel: Updated secondary planets data.");
5253
+ // Perform a deep merge for each secondary planet
5254
+ for (const planetName in data.secondaryPlanets) {
5255
+ if (this.secondaryPlanets[planetName]) {
5256
+ this.secondaryPlanets[planetName] = { ...this.secondaryPlanets[planetName], ...data.secondaryPlanets[planetName] };
5257
+ } else {
5258
+ this.secondaryPlanets[planetName] = data.secondaryPlanets[planetName];
5259
+ }
5260
+ }
5261
+ // console.log("NocturnaWheel: Updated secondary planets data (deep merged).");
5147
5262
  } else {
5148
5263
  console.warn("NocturnaWheel.updateData: Invalid secondaryPlanets data format. Expected object.");
5149
5264
  }
@@ -5156,7 +5271,7 @@ class NocturnaWheel {
5156
5271
  if (this.renderers.house) {
5157
5272
  this.renderers.house.houseData = this.houses;
5158
5273
  }
5159
- console.log("NocturnaWheel: Updated houses data.");
5274
+ // console.log("NocturnaWheel: Updated houses data.");
5160
5275
  } else {
5161
5276
  console.warn("NocturnaWheel.updateData: Invalid houses data format. Expected array.");
5162
5277
  }
@@ -5179,7 +5294,7 @@ class NocturnaWheel {
5179
5294
  this.config.updateAspectSettings(configUpdate.aspectSettings);
5180
5295
  }
5181
5296
 
5182
- console.log("NocturnaWheel: Updated configuration.");
5297
+ // console.log("NocturnaWheel: Updated configuration.");
5183
5298
  // Re-render the chart with updated configuration
5184
5299
  this.render();
5185
5300
  return this;
@@ -5227,7 +5342,7 @@ class NocturnaWheel {
5227
5342
  primaryGroup.style.display = visible ? 'block' : 'none';
5228
5343
  }
5229
5344
 
5230
- console.log(`NocturnaWheel: Primary planets ${visible ? 'enabled' : 'disabled'}`);
5345
+ // console.log(`NocturnaWheel: Primary planets ${visible ? 'enabled' : 'disabled'}`);
5231
5346
  return this;
5232
5347
  }
5233
5348
 
@@ -5252,7 +5367,7 @@ class NocturnaWheel {
5252
5367
  innermostCircle.style.display = visible ? 'block' : 'none';
5253
5368
  }
5254
5369
 
5255
- console.log(`NocturnaWheel: Secondary planets ${visible ? 'enabled' : 'disabled'}`);
5370
+ // console.log(`NocturnaWheel: Secondary planets ${visible ? 'enabled' : 'disabled'}`);
5256
5371
  return this;
5257
5372
  }
5258
5373
  }
@@ -5338,6 +5453,9 @@ class ChartRenderer {
5338
5453
  cx: centerX,
5339
5454
  cy: centerY,
5340
5455
  r: radius,
5456
+ fill: "transparent", // Explicitly set transparent fill to avoid default black
5457
+ stroke: "#999", // Explicitly set stroke to ensure visibility
5458
+ "stroke-width": "0.5", // Explicitly set stroke width
5341
5459
  class: 'zodiac-element chart-innermost-circle'
5342
5460
  });
5343
5461
  zodiacGroup.appendChild(innermostCircle);
@@ -5742,11 +5860,21 @@ function cleanup() {
5742
5860
  }
5743
5861
  }
5744
5862
 
5745
- // Initialize the chart when the DOM is ready
5746
- document.addEventListener('DOMContentLoaded', initChart);
5863
+ // Auto-initialization is DISABLED in production builds to prevent conflicts.
5864
+ // This demo code should only run in development mode with Vite dev server.
5865
+ // In production, users explicitly create their own chart instances.
5747
5866
 
5748
- // Handle hot module replacement for Vite
5867
+ // Handle hot module replacement for Vite (development only)
5749
5868
  if (import.meta.hot) {
5869
+ // Initialize the chart when the DOM is ready (ONLY in development)
5870
+ document.addEventListener('DOMContentLoaded', () => {
5871
+ const container = document.getElementById('chart-container');
5872
+ if (container && container.children.length === 0) {
5873
+ console.log('DEV MODE: Auto-initializing demo chart');
5874
+ initChart();
5875
+ }
5876
+ });
5877
+
5750
5878
  import.meta.hot.accept((newModule) => {
5751
5879
  console.log('HMR update for main.js');
5752
5880
  cleanup();