Skip to content

Commit 08939a9

Browse files
author
LoneWandererProductions
committed
Add Glyph Support Layer
1 parent bd4a139 commit 08939a9

4 files changed

Lines changed: 161 additions & 3 deletions

File tree

Solaris/Aurora.xaml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
<Image Name="LayerOne" />
1212
<Image Name="LayerTwo" />
1313
<Image Name="LayerThree" />
14+
<Image Name="LayerFour"/>
1415
<Label Name="Touch" MouseDown="Touch_MouseDown" />
1516
</Grid>
1617
</UserControl>

Solaris/Aurora.xaml.cs

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
using System.Windows.Input;
1616
using Imaging;
1717
using Mathematics;
18+
using Solaris.Solaris;
1819

1920
namespace Solaris
2021
{
@@ -106,6 +107,13 @@ public sealed partial class Aurora
106107
nameof(AuroraRemoveDisplay), typeof(int), typeof(Aurora),
107108
new PropertyMetadata(0, OnRemoveDisplayChanged));
108109

110+
/// <summary>
111+
/// The aurora glyphs property
112+
/// </summary>
113+
public static readonly DependencyProperty AuroraGlyphsProperty = DependencyProperty.Register(
114+
nameof(AuroraGlyphs), typeof(Dictionary<int, OverlayGlyph>), typeof(Aurora),
115+
new PropertyMetadata(null, OnGlyphsChanged));
116+
109117
#endregion
110118

111119
/// <summary>
@@ -285,6 +293,18 @@ public bool AuroraGrid
285293
set => SetValue(AuroraGridProperty, value);
286294
}
287295

296+
/// <summary>
297+
/// Gets or sets the aurora glyphs.
298+
/// </summary>
299+
/// <value>
300+
/// The aurora glyphs.
301+
/// </value>
302+
public Dictionary<int, OverlayGlyph>? AuroraGlyphs
303+
{
304+
get => (Dictionary<int, OverlayGlyph>?)GetValue(AuroraGlyphsProperty);
305+
set => SetValue(AuroraGlyphsProperty, value);
306+
}
307+
288308
#endregion
289309

290310
#region Dependency Property Callbacks (Safe execution)
@@ -412,6 +432,17 @@ private static void OnRemoveDisplayChanged(DependencyObject d, DependencyPropert
412432
control.LayerThree.Source = newBmp?.ToBitmapImage();
413433
}
414434

435+
/// <summary>
436+
/// Called when [glyphs changed].
437+
/// </summary>
438+
/// <param name="d">The d.</param>
439+
/// <param name="e">The <see cref="DependencyPropertyChangedEventArgs"/> instance containing the event data.</param>
440+
private static void OnGlyphsChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
441+
{
442+
var control = (Aurora)d;
443+
control.UpdateGlyphLayer();
444+
}
445+
415446
#endregion
416447

417448
#region Setup and Memory Management
@@ -468,6 +499,15 @@ private void ReplaceThirdLayer(Bitmap? newBitmap)
468499
// Only assign if required, usually overlaid later
469500
}
470501

502+
/// <summary>
503+
/// Redraws only the vector annotation layer cleanly without touching heavy ground assets.
504+
/// </summary>
505+
public void UpdateGlyphLayer()
506+
{
507+
var overlayBmp = Helper.GenerateGlyphOverlay(AuroraWidth, AuroraHeight, AuroraTextureSize, AuroraGlyphs);
508+
LayerFour.Source = overlayBmp?.ToBitmapImage();
509+
}
510+
471511
/// <summary>
472512
/// Handles the MouseDown event of the Touch control.
473513
/// </summary>
@@ -488,4 +528,4 @@ private void Touch_MouseDown(object sender, MouseButtonEventArgs e)
488528

489529
#endregion
490530
}
491-
}
531+
}

Solaris/Helper.cs

Lines changed: 60 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,16 @@
66
* PROGRAMMER: Peter Geinitz (Wayfarer)
77
*/
88

9-
using ExtendedSystemObjects;
10-
using Imaging;
119
using System;
1210
using System.Collections.Concurrent;
1311
using System.Collections.Generic;
1412
using System.Drawing;
1513
using System.Linq;
1614
using System.Threading.Tasks;
1715
using System.Windows.Media;
16+
using ExtendedSystemObjects;
17+
using Imaging;
18+
using Solaris.Solaris;
1819
using Brushes = System.Drawing.Brushes;
1920

2021
namespace Solaris
@@ -170,6 +171,63 @@ internal static ImageSource GenerateNumbers(int width, int height, int textureSi
170171
return bitmap.ToBitmapImage();
171172
}
172173

174+
/// <summary>
175+
/// Generates a transparent vector overlay layer hosting crisp numbers or Unicode symbols.
176+
/// </summary>
177+
/// <param name="width">The width.</param>
178+
/// <param name="height">The height.</param>
179+
/// <param name="textureSize">Size of the texture.</param>
180+
/// <param name="glyphMap">The glyph map.</param>
181+
/// <returns>Bitmap representing the glyph overlay.</returns>
182+
internal static Bitmap GenerateGlyphOverlay(
183+
int width, int height, int textureSize,
184+
Dictionary<int, OverlayGlyph>? glyphMap)
185+
{
186+
var overlayFrame = new Bitmap(width * textureSize, height * textureSize);
187+
188+
if (glyphMap == null || glyphMap.Count == 0) return overlayFrame;
189+
190+
using (var g = Graphics.FromImage(overlayFrame))
191+
{
192+
// THE GRIP: Enable high-fidelity vector text rendering
193+
g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
194+
g.TextRenderingHint = System.Drawing.Text.TextRenderingHint.AntiAliasGridFit;
195+
196+
// Establish string formatting rules to ensure symbols center perfectly inside the cell block
197+
using (var sf = new StringFormat())
198+
{
199+
sf.Alignment = StringAlignment.Center;
200+
sf.LineAlignment = StringAlignment.Center;
201+
202+
foreach (var kp in glyphMap)
203+
{
204+
int tileIndex = kp.Key;
205+
OverlayGlyph glyph = kp.Value;
206+
207+
if (string.IsNullOrEmpty(glyph.Symbol)) continue;
208+
209+
// Map flat index location straight into 2D chessboard pixel boundaries
210+
int cellX = (tileIndex % width) * textureSize;
211+
int cellY = (tileIndex / width) * textureSize;
212+
213+
// Calculate the exact destination boundaries of the chessboard cell space
214+
var targetRect = new RectangleF(cellX, cellY, textureSize, textureSize);
215+
216+
// Build font family profile dynamically
217+
var fontStyle = glyph.IsBold ? System.Drawing.FontStyle.Bold : System.Drawing.FontStyle.Regular;
218+
using (var font = new Font(glyph.FontName, glyph.FontSize, fontStyle))
219+
using (var brush = new SolidColorBrush(glyph.Color))
220+
{
221+
// Draw the crisp vector character straight onto the bitmap buffer plane
222+
g.DrawString(glyph.Symbol, font, brush, targetRect, sf);
223+
}
224+
}
225+
}
226+
}
227+
228+
return overlayFrame;
229+
}
230+
173231
/// <summary>
174232
/// Adds a tile to the map.
175233
/// </summary>

Solaris/OverlayGlyph.cs

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
/*
2+
* COPYRIGHT: See COPYING in the top level directory
3+
* PROJECT: Solaris
4+
* FILE: OverlayGlyph.cs
5+
* PURPOSE: Handle the overlay glyphs, which are drawn on top of the tile and can be used to display additional information like health, damage, or other status effects.
6+
* PROGRAMER: Peter Geinitz (Wayfarer)
7+
*/
8+
9+
namespace Solaris
10+
{
11+
namespace Solaris
12+
{
13+
public sealed class OverlayGlyph
14+
{
15+
/// <summary>
16+
/// Gets or sets the symbol.
17+
/// E.g., "⚔", "🪙", "💧", or "4"
18+
/// </summary>
19+
/// <value>
20+
/// The symbol.
21+
/// </value>
22+
public string Symbol { get; set; } = string.Empty;
23+
24+
/// <summary>
25+
/// Gets or sets the color.
26+
/// </summary>
27+
/// <value>
28+
/// The color.
29+
/// </value>
30+
public System.Drawing.Color Color { get; set; } = System.Drawing.Color.Gold;
31+
32+
/// <summary>
33+
/// Gets or sets the name of the font.
34+
/// Handles Unicode vectors out of the box
35+
/// </summary>
36+
/// <value>
37+
/// The name of the font.
38+
/// </value>
39+
public string FontName { get; set; } = "Segoe UI Symbol";
40+
41+
/// <summary>
42+
/// Gets or sets the size of the font.
43+
/// Scaled proportionally to match your TileSize
44+
/// </summary>
45+
/// <value>
46+
/// The size of the font.
47+
/// </value>
48+
public float FontSize { get; set; } = 14f;
49+
50+
/// <summary>
51+
/// Gets or sets a value indicating whether this instance is bold.
52+
/// </summary>
53+
/// <value>
54+
/// <c>true</c> if this instance is bold; otherwise, <c>false</c>.
55+
/// </value>
56+
public bool IsBold { get; set; } = true;
57+
}
58+
}
59+
}

0 commit comments

Comments
 (0)