JD2022-TU1/main/tools/framework/JD.Timeline/View/SnipeView/SnipingBackdataProcessor.cs

255 lines
9.2 KiB
C#

using CameraScoringFilesInfoProvider;
using System;
using System.Collections.Generic;
using System.Linq;
using TeaBox;
using JD.Serialization;
using Path = System.IO.Path;
using JD.Timeline.View.ScoreView;
using System.IO;
using JD.Core;
using JD.Core.Collections;
using JD.LogService;
using JD.Timeline.Model;
using Directory = System.IO.Directory;
namespace JD.Timeline.View.SnipeView
{
/// <summary>
/// Handles back data for sniping view
/// Keeps data of all the moves and their sniping information
/// </summary>
internal class SnipeViewModel
{
#region Fields and Properties
/// <summary>
/// Contains Sniping information for all the moves
/// Contains SnipeLabel data regarding every examples related to particular move
/// </summary>
private SnipingDatabase _moveSnipingDatabase;
/// <summary>
/// Keeps Track of the Moves for which the Sniping Information has been changed
/// Whenever saving, CSV files for all the moves in this list will be passed on for saving
/// </summary>
private readonly List<string> _movesForWhichSnipeDataEdited;
public bool IsSnipingDataAvailableToShow { get; set; }
public bool AreSnipingPrerequisitesAvailable { get; set; }
#endregion
#region Constructor
public SnipeViewModel()
{
_movesForWhichSnipeDataEdited = new List<string>();
}
#endregion
#region Public Methods
/// <summary>
/// Checks whether Database is set up
/// </summary>
/// <returns></returns>
public bool IsDatabaseSetup()
{
return (_moveSnipingDatabase != null && _moveSnipingDatabase.SnipeList != null && _moveSnipingDatabase.SnipeList.Count > 0);
}
/// <summary>
/// Sets up sniping labels according to csv files for each move
/// </summary>
public void SetupSnipingDatabase(ScoringPlatform platform, Tape tape, ILogger logger)
{
var examplesDirectory = Path.Combine(tape.Map().MovesFolder, platform.GetPlatformCode(), "Examples");
var recordingsDirectory = Path.Combine(JDDefinitions.Instance.NasScoringDirectory, tape.MapName, platform.GetPlatformName(), "Recordings");
var tweakRecordingsDirectory = Path.Combine(JDDefinitions.Instance.NasScoringDirectory, tape.MapName, platform.GetPlatformName(), "TweakRecordings");
if (_moveSnipingDatabase != null)
_moveSnipingDatabase.ClearData();
_moveSnipingDatabase = new SnipingDatabase(platform);
if (HasRecordingFiles(platform, recordingsDirectory) || HasRecordingFiles(platform, tweakRecordingsDirectory))
{
AreSnipingPrerequisitesAvailable = true;
if (Directory.Exists(examplesDirectory))
{
var exampleCsvs = Directory.GetFiles(examplesDirectory, "*.csv", SearchOption.AllDirectories).ToArray();
if (!exampleCsvs.Any())
return;
IsSnipingDataAvailableToShow = PopulateSnipeData(exampleCsvs, logger);
}
}
else
{
logger.LogError($"No Recordings found in {recordingsDirectory} and {tweakRecordingsDirectory}");
IsSnipingDataAvailableToShow = false;
AreSnipingPrerequisitesAvailable = false;
}
}
private static bool HasRecordingFiles(ScoringPlatform platform, string recordingsDirectory)
{
if (!Directory.Exists(recordingsDirectory))
return false;
return Directory.EnumerateFiles(recordingsDirectory, platform.GetFileExtensionForRecording()).Any();
}
/// <summary>
/// Disposes Sniping Database of a particular platform
/// </summary>
public void DisposeSnipingDatabase()
{
if (_moveSnipingDatabase.SnipeList == null)
throw new ArgumentNullException();
foreach (var snipeData in _moveSnipingDatabase.SnipeList)
{
snipeData.SnipingDataChanged -= OnSnipingDataChanged;
}
_moveSnipingDatabase.ClearData();
}
/// <summary>
/// Fills sniping data in the database
/// </summary>
/// <param name="exampleCsvs"></param>
/// <param name="logger"></param>
/// <returns></returns>
public bool PopulateSnipeData(string[] exampleCsvs, ILogger logger)
{
_moveSnipingDatabase.SnipeList = SnipingDataFilesProcessor.CreateSnipingDatabaseFromAllCsvFiles(exampleCsvs, logger);
return (_moveSnipingDatabase.SnipeList != null && _moveSnipingDatabase.SnipeList.Count > 0);
}
/// <summary>
/// Sets sniping info over an example for given move
/// </summary>
/// <param name="moveName"></param>
/// <param name="fileName"></param>
/// <param name="label"></param>
/// <returns></returns>
public bool SetLabelForExample(string moveName, string fileName, SnipeLabel label)
{
if (_moveSnipingDatabase.SnipeList.Any(item => item.MoveName == moveName))
{
var snipingData = _moveSnipingDatabase.SnipeList.First(item => item.MoveName == moveName);
var fileNameOnly = Path.GetFileNameWithoutExtension(fileName);
if (snipingData != null)
{
snipingData.TaggedExamplesList.First(item => item.FileNameOnly == fileNameOnly).SnipeLabel = label;
return true;
}
}
return false;
}
/// <summary>
/// Registers handler for checking changes in Sniping data
/// </summary>
public void RegisterActionWhenSnipeDataIsChanged()
{
//Start checking for any changes made in current view
foreach (var moveSnipeData in _moveSnipingDatabase.SnipeList)
{
moveSnipeData.SnipingDataChanged += OnSnipingDataChanged;
}
}
/// <summary>
/// Gets the Sniping info for a given example file
/// </summary>
/// <param name="exampleFileInfo"></param>
/// <returns></returns>
public MoveExampleClip.CurrentSnipeStatus_Enum GetSnipeStatus(ExampleFileInfo exampleFileInfo)
{
if (_moveSnipingDatabase.SnipeList.Any(item => item.MoveName == exampleFileInfo.MoveName))
{
var moveSnipeData = _moveSnipingDatabase.SnipeList.Find(item => item.MoveName == exampleFileInfo.MoveName);
var snipeList = moveSnipeData.TaggedExamplesList;
if (snipeList.Any(item => item.FileNameOnly == exampleFileInfo.SessionFileNameOnly))
{
var snipeInfo = snipeList.First(item => item.FileNameOnly == exampleFileInfo.SessionFileNameOnly);
return (MoveExampleClip.CurrentSnipeStatus_Enum)snipeInfo.SnipeLabel;
}
}
return MoveExampleClip.CurrentSnipeStatus_Enum.Ignored;
}
/// <summary>
/// Checks whether score data is edited or not
/// </summary>
/// <param name="allEditedSnipeData"></param>
/// <returns></returns>
public bool IsScoreDataEdited(out List<MoveSnipingData> allEditedSnipeData)
{
allEditedSnipeData = (from snipeData in _moveSnipingDatabase.SnipeList
from moveName in _movesForWhichSnipeDataEdited
where snipeData.MoveName == moveName
select snipeData).ToList();
return allEditedSnipeData.Count > 0;
}
/// <summary>
/// Uses SnipingDataFilesProcessor to save edited sniping data to appropriate Csv files
/// </summary>
/// <param name="logger"></param>
public void SaveEditedData(ILogger logger)
{
try
{
List<MoveSnipingData> allEditedSnipeData;
if (IsScoreDataEdited(out allEditedSnipeData))
{
foreach (var snipeData in allEditedSnipeData)
{
if (SnipingDataFilesProcessor.SaveSnipeDataToCsvFile(snipeData, logger))
{
_movesForWhichSnipeDataEdited.Remove(snipeData.MoveName);
}
}
}
}
catch (Exception ex)
{
logger.LogError("Error while saving csv files for edited sniped data : " + ex.Message);
throw;
}
}
#endregion
#region Private Methods
private void OnSnipingDataChanged(object sender, ItemChangedEventArgs<SnipeInfo> args)
{
var snipingData = sender as MoveSnipingData;
if (snipingData != null && !_movesForWhichSnipeDataEdited.Contains(snipingData.MoveName))
_movesForWhichSnipeDataEdited.Add(snipingData.MoveName);
}
#endregion
}
}