- .NET 8 WPF app with full MVVM architecture - One-click boost: CPU, RAM, GPU, network, services, timer resolution - Real-time system monitor (LibreHardwareMonitor) - Auto game detection (30+ games) - RAM optimizer with kernel-level cleanup - Network optimizer (TCP registry tweaks) - Service manager, process manager, shader cache cleaner - Desktop widget overlay - Debug log viewer - Custom dark gaming theme with trans pride colors - 84 unit tests (xUnit) - Inno Setup installer script - Landing page website
111 lines
3.9 KiB
C#
111 lines
3.9 KiB
C#
using System.IO;
|
||
using SpdUp.Core;
|
||
|
||
namespace SpdUp.Services;
|
||
|
||
/// <summary>
|
||
/// Cleans DirectX shader cache, NVIDIA shader cache, and temp files
|
||
/// to reduce micro-stuttering in games.
|
||
/// </summary>
|
||
public static class ShaderCacheCleanerService
|
||
{
|
||
public static ShaderCleanResult CleanAll()
|
||
{
|
||
long totalBytes = 0;
|
||
int totalFiles = 0;
|
||
|
||
totalBytes += CleanDirectory(GetDirectXShaderCachePath(), ref totalFiles);
|
||
totalBytes += CleanDirectory(GetNvidiaShaderCachePath(), ref totalFiles);
|
||
totalBytes += CleanDirectory(GetWindowsTempPath(), ref totalFiles);
|
||
totalBytes += CleanDirectory(GetLocalTempPath(), ref totalFiles);
|
||
|
||
Logger.Info($"Shader cache clean: {totalFiles} files, {totalBytes / 1048576.0:F1} MB freed.");
|
||
return new ShaderCleanResult(totalFiles, totalBytes);
|
||
}
|
||
|
||
public static ShaderCleanResult CleanDirectXCache()
|
||
{
|
||
long totalBytes = 0;
|
||
int totalFiles = 0;
|
||
totalBytes += CleanDirectory(GetDirectXShaderCachePath(), ref totalFiles);
|
||
return new ShaderCleanResult(totalFiles, totalBytes);
|
||
}
|
||
|
||
public static ShaderCleanResult CleanNvidiaCache()
|
||
{
|
||
long totalBytes = 0;
|
||
int totalFiles = 0;
|
||
totalBytes += CleanDirectory(GetNvidiaShaderCachePath(), ref totalFiles);
|
||
return new ShaderCleanResult(totalFiles, totalBytes);
|
||
}
|
||
|
||
public static ShaderCleanResult CleanTempFiles()
|
||
{
|
||
long totalBytes = 0;
|
||
int totalFiles = 0;
|
||
totalBytes += CleanDirectory(GetWindowsTempPath(), ref totalFiles);
|
||
totalBytes += CleanDirectory(GetLocalTempPath(), ref totalFiles);
|
||
return new ShaderCleanResult(totalFiles, totalBytes);
|
||
}
|
||
|
||
// ── Paths ──────────────────────────────────────────────────────────
|
||
private static string GetDirectXShaderCachePath()
|
||
=> Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData),
|
||
"D3DSCache");
|
||
|
||
private static string GetNvidiaShaderCachePath()
|
||
=> Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.LocalApplicationData),
|
||
"NVIDIA", "DXCache");
|
||
|
||
private static string GetWindowsTempPath()
|
||
=> Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Windows), "Temp");
|
||
|
||
private static string GetLocalTempPath()
|
||
=> Path.GetTempPath();
|
||
|
||
// ── Helpers ────────────────────────────────────────────────────────
|
||
private static long CleanDirectory(string path, ref int fileCount)
|
||
{
|
||
if (!Directory.Exists(path)) return 0;
|
||
long bytes = 0;
|
||
|
||
try
|
||
{
|
||
foreach (var file in Directory.EnumerateFiles(path, "*", SearchOption.AllDirectories))
|
||
{
|
||
try
|
||
{
|
||
var fi = new FileInfo(file);
|
||
bytes += fi.Length;
|
||
fi.Delete();
|
||
fileCount++;
|
||
}
|
||
catch { /* locked / in use – skip */ }
|
||
}
|
||
|
||
// Remove empty dirs
|
||
foreach (var dir in Directory.EnumerateDirectories(path, "*", SearchOption.AllDirectories)
|
||
.OrderByDescending(d => d.Length))
|
||
{
|
||
try
|
||
{
|
||
if (!Directory.EnumerateFileSystemEntries(dir).Any())
|
||
Directory.Delete(dir);
|
||
}
|
||
catch { }
|
||
}
|
||
}
|
||
catch (Exception ex)
|
||
{
|
||
Logger.Warn($"Error cleaning {path}: {ex.Message}");
|
||
}
|
||
|
||
return bytes;
|
||
}
|
||
}
|
||
|
||
public record struct ShaderCleanResult(int FilesDeleted, long BytesFreed)
|
||
{
|
||
public double MBFreed => BytesFreed / 1048576.0;
|
||
}
|