Sono stati aggiunti tutti i file principali di Bootstrap 5.3.3, inclusi CSS, JavaScript (bundle, ESM, UMD, minificati), versioni RTL, utility, reboot, griglia e relative mappe delle sorgenti. Questi file abilitano un sistema di design moderno, responsive e accessibile, con supporto per layout LTR e RTL, debugging avanzato tramite source map e tutte le funzionalità di Bootstrap per lo sviluppo dell’interfaccia utente. Nessuna modifica ai file esistenti.
129 lines
4.3 KiB
Plaintext
129 lines
4.3 KiB
Plaintext
@using TradingBot.Models
|
|
|
|
<div class="advanced-chart">
|
|
@if (PriceData == null || PriceData.Count < 2)
|
|
{
|
|
<div class="chart-loading">
|
|
<div class="loading-spinner"></div>
|
|
<span>In attesa di dati sufficienti...</span>
|
|
</div>
|
|
}
|
|
else
|
|
{
|
|
<svg viewBox="0 0 @Width @Height" class="chart-svg" preserveAspectRatio="none">
|
|
<defs>
|
|
<linearGradient id="gradient-@ColorId" x1="0%" y1="0%" x2="0%" y2="100%">
|
|
<stop offset="0%" stop-color="@Color" stop-opacity="0.4" />
|
|
<stop offset="100%" stop-color="@Color" stop-opacity="0.05" />
|
|
</linearGradient>
|
|
</defs>
|
|
|
|
<!-- Grid Lines -->
|
|
@for (int i = 0; i <= 4; i++)
|
|
{
|
|
var y = (Height * i / 4.0);
|
|
<line x1="0" y1="@y" x2="@Width" y2="@y"
|
|
stroke="rgba(51, 65, 85, 0.3)" stroke-width="1" stroke-dasharray="4 4" />
|
|
}
|
|
|
|
<!-- Area Fill -->
|
|
@if (!string.IsNullOrEmpty(GetAreaPath()))
|
|
{
|
|
<path d="@GetAreaPath()" fill="url(#gradient-@ColorId)" />
|
|
}
|
|
|
|
<!-- Line Chart -->
|
|
@if (!string.IsNullOrEmpty(GetPolylinePoints()))
|
|
{
|
|
<polyline fill="none" stroke="@Color" stroke-width="3"
|
|
points="@GetPolylinePoints()"
|
|
stroke-linecap="round" stroke-linejoin="round" />
|
|
}
|
|
</svg>
|
|
|
|
@if (Indicators != null)
|
|
{
|
|
<div class="indicators-overlay">
|
|
<div class="indicator-badge">
|
|
<span class="indicator-label">RSI:</span>
|
|
<span class="indicator-value @GetRSIClass()">@Indicators.RSI.ToString("F1")</span>
|
|
</div>
|
|
<div class="indicator-badge">
|
|
<span class="indicator-label">MACD:</span>
|
|
<span class="indicator-value">@Indicators.MACD.ToString("F2")</span>
|
|
</div>
|
|
</div>
|
|
}
|
|
}
|
|
</div>
|
|
|
|
@code {
|
|
[Parameter] public List<decimal>? PriceData { get; set; }
|
|
[Parameter] public string Color { get; set; } = "#6366f1";
|
|
[Parameter] public TechnicalIndicators? Indicators { get; set; }
|
|
|
|
private int Width = 800;
|
|
private int Height = 300;
|
|
private string ColorId => Guid.NewGuid().ToString("N").Substring(0, 8);
|
|
|
|
private string GetPolylinePoints()
|
|
{
|
|
if (PriceData == null || PriceData.Count < 2) return string.Empty;
|
|
|
|
try
|
|
{
|
|
var max = PriceData.Max();
|
|
var min = PriceData.Min();
|
|
var range = max - min;
|
|
if (range == 0) range = max * 0.01m; // 1% range if all values are same
|
|
|
|
var points = new List<string>();
|
|
var padding = Height * 0.1; // 10% padding
|
|
var chartHeight = Height - (padding * 2);
|
|
|
|
for (int i = 0; i < PriceData.Count; i++)
|
|
{
|
|
var x = (i / (double)(PriceData.Count - 1)) * Width;
|
|
var normalizedValue = (double)((PriceData[i] - min) / range);
|
|
var y = padding + (chartHeight * (1 - normalizedValue));
|
|
points.Add($"{x:F2},{y:F2}");
|
|
}
|
|
|
|
return string.Join(" ", points);
|
|
}
|
|
catch
|
|
{
|
|
return string.Empty;
|
|
}
|
|
}
|
|
|
|
private string GetAreaPath()
|
|
{
|
|
var polyline = GetPolylinePoints();
|
|
if (string.IsNullOrEmpty(polyline)) return string.Empty;
|
|
|
|
try
|
|
{
|
|
var points = polyline.Split(' ');
|
|
if (points.Length < 2) return string.Empty;
|
|
|
|
var firstPoint = points[0].Split(',');
|
|
var lastPoint = points[points.Length - 1].Split(',');
|
|
|
|
return $"M {firstPoint[0]},{Height} L {polyline} L {lastPoint[0]},{Height} Z";
|
|
}
|
|
catch
|
|
{
|
|
return string.Empty;
|
|
}
|
|
}
|
|
|
|
private string GetRSIClass()
|
|
{
|
|
if (Indicators == null) return "rsi-neutral";
|
|
if (Indicators.RSI > 70) return "rsi-overbought";
|
|
if (Indicators.RSI < 30) return "rsi-oversold";
|
|
return "rsi-neutral";
|
|
}
|
|
}
|