250 lines
8.1 KiB
C#
250 lines
8.1 KiB
C#
using System.Collections.Generic;
|
||
using System.IO;
|
||
using System.Linq;
|
||
using AIImages.Components;
|
||
using UnityEngine;
|
||
using Verse;
|
||
|
||
namespace AIImages.Helpers
|
||
{
|
||
/// <summary>
|
||
/// Вспомогательный класс для работы с портретами персонажей
|
||
/// </summary>
|
||
public static class PawnPortraitHelper
|
||
{
|
||
/// <summary>
|
||
/// Получить компонент портрета пешки
|
||
/// </summary>
|
||
public static PawnPortraitComp GetPortraitComp(Pawn pawn)
|
||
{
|
||
if (pawn == null)
|
||
{
|
||
DebugLogger.Warning("[AI Images] GetPortraitComp called with null pawn");
|
||
return null;
|
||
}
|
||
|
||
var comp = pawn.TryGetComp<PawnPortraitComp>();
|
||
DebugLogger.Log(
|
||
$"[AI Images] GetPortraitComp for {pawn.Name}: {(comp != null ? "Found" : "Not found")}"
|
||
);
|
||
return comp;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Сохранить путь к портрету на пешке (добавляет в галерею)
|
||
/// </summary>
|
||
public static void SavePortraitPath(Pawn pawn, string path)
|
||
{
|
||
DebugLogger.Log(
|
||
$"[AI Images] SavePortraitPath called for {pawn?.Name} with path: {path}"
|
||
);
|
||
|
||
var comp = GetPortraitComp(pawn);
|
||
if (comp != null)
|
||
{
|
||
comp.AddPortrait(path);
|
||
DebugLogger.Log(
|
||
$"[AI Images] Successfully added portrait path for {pawn.Name}: {path}"
|
||
);
|
||
DebugLogger.Log($"[AI Images] Component now has {comp.PortraitCount} portraits");
|
||
}
|
||
else
|
||
{
|
||
DebugLogger.Error($"[AI Images] Failed to get portrait component for {pawn?.Name}");
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// Получить путь к портрету пешки
|
||
/// </summary>
|
||
public static string GetPortraitPath(Pawn pawn)
|
||
{
|
||
DebugLogger.Log($"[AI Images] GetPortraitPath called for {pawn?.Name}");
|
||
|
||
var comp = GetPortraitComp(pawn);
|
||
if (comp == null)
|
||
{
|
||
DebugLogger.Warning($"[AI Images] No portrait component found for {pawn?.Name}");
|
||
return null;
|
||
}
|
||
|
||
DebugLogger.Log(
|
||
$"[AI Images] Portrait component found for {pawn?.Name}, path: '{comp.PortraitPath}'"
|
||
);
|
||
return comp.PortraitPath;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Есть ли у пешки сохраненный портрет
|
||
/// </summary>
|
||
public static bool HasPortrait(Pawn pawn)
|
||
{
|
||
DebugLogger.Log($"[AI Images] HasPortrait called for {pawn?.Name}");
|
||
|
||
var comp = GetPortraitComp(pawn);
|
||
if (comp == null)
|
||
{
|
||
DebugLogger.Log($"[AI Images] No portrait component found for {pawn?.Name}");
|
||
return false;
|
||
}
|
||
|
||
bool hasPortrait = comp.HasPortrait;
|
||
DebugLogger.Log(
|
||
$"[AI Images] Portrait component for {pawn?.Name} has portrait: {hasPortrait} (path: '{comp.PortraitPath}')"
|
||
);
|
||
return hasPortrait;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Загрузить портрет пешки как текстуру
|
||
/// </summary>
|
||
public static Texture2D LoadPortrait(Pawn pawn)
|
||
{
|
||
DebugLogger.Log($"[AI Images] LoadPortrait called for {pawn?.Name}");
|
||
|
||
string path = GetPortraitPath(pawn);
|
||
DebugLogger.Log($"[AI Images] Retrieved path for {pawn?.Name}: '{path}'");
|
||
|
||
if (string.IsNullOrEmpty(path))
|
||
{
|
||
DebugLogger.Log($"[AI Images] No portrait path found for {pawn?.Name}");
|
||
return null;
|
||
}
|
||
|
||
if (!File.Exists(path))
|
||
{
|
||
DebugLogger.Warning(
|
||
$"[AI Images] Portrait file does not exist for {pawn?.Name}: {path}"
|
||
);
|
||
return null;
|
||
}
|
||
|
||
DebugLogger.Log($"[AI Images] Portrait file exists for {pawn?.Name}: {path}");
|
||
|
||
try
|
||
{
|
||
byte[] imageData = File.ReadAllBytes(path);
|
||
DebugLogger.Log(
|
||
$"[AI Images] Successfully read {imageData.Length} bytes from {path}"
|
||
);
|
||
|
||
Texture2D texture = new Texture2D(2, 2);
|
||
texture.LoadImage(imageData);
|
||
DebugLogger.Log(
|
||
$"[AI Images] Successfully loaded texture for {pawn?.Name}, size: {texture.width}x{texture.height}"
|
||
);
|
||
return texture;
|
||
}
|
||
catch (System.Exception ex)
|
||
{
|
||
DebugLogger.Warning(
|
||
$"[AI Images] Failed to load portrait for {pawn?.Name}: {ex.Message}"
|
||
);
|
||
return null;
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// Очистить портрет пешки (удаляет все портреты)
|
||
/// </summary>
|
||
public static void ClearPortrait(Pawn pawn)
|
||
{
|
||
var comp = GetPortraitComp(pawn);
|
||
if (comp != null)
|
||
{
|
||
comp.ClearPortraits();
|
||
}
|
||
}
|
||
|
||
/// <summary>
|
||
/// Получить все пути к портретам пешки (галерея)
|
||
/// </summary>
|
||
public static List<string> GetAllPortraits(Pawn pawn)
|
||
{
|
||
var comp = GetPortraitComp(pawn);
|
||
return comp?.GetAllPortraits() ?? new List<string>();
|
||
}
|
||
|
||
/// <summary>
|
||
/// Получить количество портретов в галерее
|
||
/// </summary>
|
||
public static int GetPortraitCount(Pawn pawn)
|
||
{
|
||
var comp = GetPortraitComp(pawn);
|
||
return comp?.PortraitCount ?? 0;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Удалить конкретный портрет из галереи
|
||
/// </summary>
|
||
public static bool RemovePortrait(Pawn pawn, string path)
|
||
{
|
||
var comp = GetPortraitComp(pawn);
|
||
return comp?.RemovePortrait(path) ?? false;
|
||
}
|
||
|
||
/// <summary>
|
||
/// Очистить все сгенерированные портреты
|
||
/// </summary>
|
||
public static int ClearAllPortraits(string savePath)
|
||
{
|
||
ClearPawnComponents();
|
||
return DeletePortraitFiles(savePath);
|
||
}
|
||
|
||
private static void ClearPawnComponents()
|
||
{
|
||
if (Current.Game?.Maps == null)
|
||
return;
|
||
|
||
foreach (var map in Current.Game.Maps)
|
||
{
|
||
foreach (var pawn in map.mapPawns.AllPawns)
|
||
{
|
||
var comp = GetPortraitComp(pawn);
|
||
if (comp != null && comp.HasPortrait)
|
||
{
|
||
comp.ClearPortraits();
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
private static int DeletePortraitFiles(string savePath)
|
||
{
|
||
int deletedCount = 0;
|
||
string fullPath = Path.Combine(GenFilePaths.SaveDataFolderPath, savePath);
|
||
|
||
if (!Directory.Exists(fullPath))
|
||
return deletedCount;
|
||
|
||
try
|
||
{
|
||
var files = Directory.GetFiles(fullPath, "*.png");
|
||
deletedCount = files.Count(TryDeleteFile);
|
||
Log.Message($"[AI Images] Deleted {deletedCount} portrait files");
|
||
}
|
||
catch (System.Exception ex)
|
||
{
|
||
Log.Error($"[AI Images] Error cleaning portraits directory: {ex.Message}");
|
||
}
|
||
|
||
return deletedCount;
|
||
}
|
||
|
||
private static bool TryDeleteFile(string file)
|
||
{
|
||
try
|
||
{
|
||
File.Delete(file);
|
||
return true;
|
||
}
|
||
catch (System.Exception ex)
|
||
{
|
||
Log.Warning($"[AI Images] Failed to delete file {file}: {ex.Message}");
|
||
return false;
|
||
}
|
||
}
|
||
}
|
||
}
|