Skip to content

Commit 7c960be

Browse files
Merge pull request #283 from Pear-231/AudioEditorBugfixes
Audio editor bugfixes
2 parents a022dc6 + c7d509c commit 7c960be

19 files changed

+204
-51
lines changed
Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
using System.Collections.Generic;
2+
using System.Data;
3+
using Editors.Audio.AudioEditor.Core;
4+
using Editors.Audio.AudioEditor.Core.AudioProjectMutation;
5+
using Editors.Audio.AudioEditor.Presentation.Shared;
6+
using Editors.Audio.AudioEditor.Presentation.Shared.Table;
7+
using Editors.Audio.Shared.AudioProject.Models;
8+
using Editors.Audio.Shared.Storage;
9+
using HircSettings = Editors.Audio.Shared.AudioProject.Models.HircSettings;
10+
11+
namespace Editors.Audio.AudioEditor.Commands
12+
{
13+
public class AddDialogueEventByPasteCommand(
14+
IAudioEditorStateService audioEditorStateService,
15+
IAudioRepository audioRepository,
16+
IDialogueEventService dialogueEventService) : IAudioProjectMutationUICommand
17+
{
18+
private readonly IAudioEditorStateService _audioEditorStateService = audioEditorStateService;
19+
private readonly IAudioRepository _audioRepository = audioRepository;
20+
private readonly IDialogueEventService _dialogueEventService = dialogueEventService;
21+
22+
public MutationType Action => MutationType.AddByPaste;
23+
public AudioProjectTreeNodeType NodeType => AudioProjectTreeNodeType.DialogueEvent;
24+
25+
public void Execute(DataRow row)
26+
{
27+
var audioProject = _audioEditorStateService.AudioProject;
28+
var copiedFromAudioProjectExplorerNode = _audioEditorStateService.CopiedFromAudioProjectExplorerNode;
29+
30+
HircSettings hircSettings = null;
31+
var audioFiles = new List<AudioFile>();
32+
33+
var dialogueEventName = copiedFromAudioProjectExplorerNode.Name;
34+
var dialogueEvent = _audioEditorStateService.AudioProject.GetDialogueEvent(dialogueEventName);
35+
var statePathName = TableHelpers.GetStatePathNameFromRow(row, _audioRepository, dialogueEventName);
36+
var statePath = dialogueEvent.GetStatePath(statePathName);
37+
var soundBank = _audioEditorStateService.AudioProject.GetSoundBank(copiedFromAudioProjectExplorerNode.Parent.Parent.Name);
38+
39+
if (statePath.TargetHircTypeIsSound())
40+
{
41+
var sound = soundBank.GetSound(statePath.TargetHircId);
42+
hircSettings = sound.HircSettings;
43+
audioFiles.Add(audioProject.GetAudioFile(sound.SourceId));
44+
}
45+
else if (statePath.TargetHircTypeIsRandomSequenceContainer())
46+
{
47+
var randomSequenceContainer = soundBank.GetRandomSequenceContainer(statePath.TargetHircId);
48+
hircSettings = randomSequenceContainer.HircSettings;
49+
audioFiles = audioProject.GetAudioFiles(soundBank, randomSequenceContainer);
50+
}
51+
52+
var statePathList = new List<KeyValuePair<string, string>>();
53+
foreach (DataColumn dataColumn in row.Table.Columns)
54+
{
55+
var columnNameWithQualifier = TableHelpers.DeduplicateUnderscores(dataColumn.ColumnName);
56+
var stateGroupName = TableHelpers.GetStateGroupFromStateGroupWithQualifier(_audioRepository, dialogueEventName, columnNameWithQualifier);
57+
var stateName = TableHelpers.GetValueFromRow(row, dataColumn.ColumnName);
58+
statePathList.Add(new KeyValuePair<string, string>(stateGroupName, stateName));
59+
}
60+
61+
_dialogueEventService.AddStatePath(_audioEditorStateService.SelectedAudioProjectExplorerNode.Name, audioFiles, hircSettings, statePathList);
62+
}
63+
}
64+
}

Editors/Audio/AudioEditor/Commands/AddDialogueEventCommand.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -26,17 +26,17 @@ public void Execute(DataRow row)
2626
var audioFiles = _audioEditorStateService.AudioFiles;
2727
var settings = _audioEditorStateService.HircSettings;
2828

29-
var stateLookupByStateGroup = new Dictionary<string, string>();
29+
var statePathList = new List<KeyValuePair<string, string>>();
3030
var stateGroupsWithQualifiers = _audioRepository.QualifiedStateGroupByStateGroupByDialogueEvent[dialogueEventName];
3131
foreach (var stateGroupWithQualifier in stateGroupsWithQualifiers)
3232
{
3333
var stateGroupName = TableHelpers.GetStateGroupFromStateGroupWithQualifier(_audioRepository, dialogueEventName, stateGroupWithQualifier.Key);
3434
var columnName = TableHelpers.DuplicateUnderscores(stateGroupWithQualifier.Key);
3535
var stateName = TableHelpers.GetValueFromRow(row, columnName);
36-
stateLookupByStateGroup.Add(stateGroupName, stateName);
36+
statePathList.Add(new KeyValuePair<string, string>(stateGroupName, stateName));
3737
}
3838

39-
_dialogueEventService.AddStatePath(dialogueEventName, audioFiles, settings, stateLookupByStateGroup);
39+
_dialogueEventService.AddStatePath(dialogueEventName, audioFiles, settings, statePathList);
4040
}
4141
}
4242
}

Editors/Audio/AudioEditor/Commands/AudioProjectMutationUICommandFactory.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ namespace Editors.Audio.AudioEditor.Commands
1010
public enum MutationType
1111
{
1212
Add,
13+
AddByPaste,
1314
Remove
1415
}
1516

Editors/Audio/AudioEditor/Commands/PasteViewerRowsCommand.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ public void Execute(List<DataRow> copiedRows)
2020
var selectedAudioProjectExplorerNode = _audioEditorStateService.SelectedAudioProjectExplorerNode;
2121
foreach (var row in copiedRows)
2222
{
23-
_audioProjectMutationUICommandFactory.Create(MutationType.Add, selectedAudioProjectExplorerNode.Type).Execute(row);
23+
_audioProjectMutationUICommandFactory.Create(MutationType.AddByPaste, selectedAudioProjectExplorerNode.Type).Execute(row);
2424
_eventHub.Publish(new ViewerTableRowAddRequestedEvent(row));
2525
_eventHub.Publish(new EditorAddRowButtonEnablementUpdateRequestedEvent());
2626
}

Editors/Audio/AudioEditor/Core/AudioEditorFileService.cs

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -76,8 +76,11 @@ public void Load(AudioProjectFile audioProject, string fileName, string filePath
7676

7777
var fileNameWithoutExtension = Path.GetFileNameWithoutExtension(fileName);
7878

79+
// We add the Audio Project name as a suffix to all SoundBank names so if the Audio Project name has changed we need to update them
80+
_audioEditorIntegrityService.UpdateSoundBankNames(audioProject, fileNameWithoutExtension);
81+
7982
// We create a 'dirty' Audio Project to display the whole model in the Audio Project Explorer rather than
80-
// just the clean data from the loaded Audio Project as when it's saved any unused parts are removed.
83+
// just the clean data from the loaded Audio Project as any unused parts are removed when it's saved
8184
var currentGame = _applicationSettingsService.CurrentSettings.CurrentGame;
8285
var dirtyAudioProject = AudioProjectFile.Create(audioProject, currentGame, fileNameWithoutExtension);
8386

Editors/Audio/AudioEditor/Core/AudioEditorIntegrityService.cs

Lines changed: 32 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -14,10 +14,11 @@ namespace Editors.Audio.AudioEditor.Core
1414
{
1515
public interface IAudioEditorIntegrityService
1616
{
17+
void UpdateSoundBankNames(AudioProjectFile audioProject, string audioProjectNameWithoutExtension);
1718
void CheckDialogueEventInformationIntegrity(List<Wh3DialogueEventDefinition> dialogueEventData);
1819
void CheckAudioProjectDialogueEventIntegrity(AudioProjectFile audioProject);
1920
void CheckAudioProjectWavFilesIntegrity(AudioProjectFile audioProject);
20-
void CheckAudioProjectDataIntegrity(AudioProjectFile audioProject, string audioProjectFileNameWithoutExtension);
21+
void CheckAudioProjectDataIntegrity(AudioProjectFile audioProject, string audioProjectNameWithoutExtension);
2122
void CheckMergingSoundBanksIdIntegrity();
2223
}
2324

@@ -26,6 +27,20 @@ public class AudioEditorIntegrityService(IPackFileService packFileService, IAudi
2627
private readonly IPackFileService _packFileService = packFileService;
2728
private readonly IAudioRepository _audioRepository = audioRepository;
2829

30+
public void UpdateSoundBankNames(AudioProjectFile audioProject, string audioProjectNameWithoutExtension)
31+
{
32+
foreach (var soundBank in audioProject.SoundBanks)
33+
{
34+
var soundBankAudioProjectName = Wh3SoundBankInformation.GetAudioProjectNameFromSoundBankWithAudioProjectName(soundBank.Name);
35+
if (audioProjectNameWithoutExtension != soundBankAudioProjectName)
36+
{
37+
var gameSoundBankName = Wh3SoundBankInformation.GetSoundBankNameFromSoundBankWithAudioProjectName(soundBank.Name);
38+
var correctSoundBankName = $"{gameSoundBankName}_{audioProjectNameWithoutExtension}";
39+
soundBank.Name = correctSoundBankName;
40+
}
41+
}
42+
}
43+
2944
public void CheckDialogueEventInformationIntegrity(List<Wh3DialogueEventDefinition> information)
3045
{
3146
var exclusions = new List<string> { "New_Dialogue_Event", "Battle_Individual_Melee_Weapon_Hit" };
@@ -130,7 +145,7 @@ public void CheckAudioProjectWavFilesIntegrity(AudioProjectFile audioProject)
130145
}
131146
}
132147

133-
public void CheckAudioProjectDataIntegrity(AudioProjectFile audioProject, string audioProjectFileNameWithoutExtension)
148+
public void CheckAudioProjectDataIntegrity(AudioProjectFile audioProject, string audioProjectNameWithoutExtension)
134149
{
135150
var usedHircIds = new HashSet<uint>();
136151
var usedSourceIds = new HashSet<uint>();
@@ -200,7 +215,7 @@ public void CheckAudioProjectDataIntegrity(AudioProjectFile audioProject, string
200215

201216
foreach (var soundBank in audioProject.SoundBanks)
202217
{
203-
ResolveSoundBankDataIntegrity(audioProject, audioProjectFileNameWithoutExtension, soundBank);
218+
ResolveSoundBankDataIntegrity(audioProject, audioProjectNameWithoutExtension, soundBank);
204219

205220
if (soundBank.ActionEvents != null)
206221
ResolveActionEventDataIntegrity(usedHircIds, usedSourceIds, soundBank);
@@ -215,17 +230,17 @@ public void CheckAudioProjectDataIntegrity(AudioProjectFile audioProject, string
215230
ResolveStateGroupDataIntegrity(audioProject);
216231
}
217232

218-
private static void ResolveSoundBankDataIntegrity(AudioProjectFile audioProject, string audioProjectFileNameWithoutExtension, SoundBank soundBank)
233+
private static void ResolveSoundBankDataIntegrity(AudioProjectFile audioProject, string audioProjectNameWithoutExtension, SoundBank soundBank)
219234
{
220235
if (soundBank == null)
221236
throw new InvalidOperationException("SoundBank should not be null.");
222237

223238
if (string.IsNullOrWhiteSpace(soundBank.Name))
224239
throw new InvalidOperationException("SoundBank.Name should not be null or empty.");
225240

226-
var gameSoundBankName = Wh3SoundBankInformation.GetSoundBankNameFromPrefix(soundBank.Name);
241+
var gameSoundBankName = Wh3SoundBankInformation.GetSoundBankNameFromSoundBankWithAudioProjectName(soundBank.Name);
227242
var gameSoundBank = Wh3SoundBankInformation.GetSoundBank(gameSoundBankName);
228-
var correctSoundBankName = $"{gameSoundBankName}_{audioProjectFileNameWithoutExtension}";
243+
var correctSoundBankName = $"{gameSoundBankName}_{audioProjectNameWithoutExtension}";
229244

230245
if (soundBank.Name != correctSoundBankName)
231246
throw new InvalidOperationException($"SoundBank.Name is incorrect. Expected '{correctSoundBankName}'.");
@@ -573,6 +588,17 @@ public void CheckMergingSoundBanksIdIntegrity()
573588
hasClashes = true;
574589
messageBuilder.AppendLine($"Language: {languageName}");
575590

591+
var conflictingBnks = clashingIdsById.Values
592+
.SelectMany(bnkNames => bnkNames)
593+
.Concat(clashingSourceIdsById.Values.SelectMany(bnkNames => bnkNames))
594+
.Distinct(StringComparer.OrdinalIgnoreCase)
595+
.OrderBy(name => name, StringComparer.OrdinalIgnoreCase);
596+
597+
foreach (var conflictingBnk in conflictingBnks)
598+
messageBuilder.AppendLine(conflictingBnk);
599+
600+
messageBuilder.AppendLine();
601+
576602
foreach (var sourceBnk in idsByBnk.Keys
577603
.Union(sourceIdsByBnk.Keys, StringComparer.OrdinalIgnoreCase)
578604
.OrderBy(name => name, StringComparer.OrdinalIgnoreCase))

Editors/Audio/AudioEditor/Core/AudioEditorStateService.cs

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ public interface IAudioEditorStateService
1414

1515
// Audio Project Explorer
1616
AudioProjectTreeNode SelectedAudioProjectExplorerNode { get; set; }
17+
AudioProjectTreeNode CopiedFromAudioProjectExplorerNode { get; set; }
1718

1819
// Audio Project Editor
1920
bool ShowModdedStatesOnly { get; set; }
@@ -30,6 +31,7 @@ public interface IAudioEditorStateService
3031
public void StoreAudioProjectFileName(string audioProjectFileName);
3132
public void StoreAudioProjectFilePath(string audioProjectFilePath);
3233
void StoreSelectedAudioProjectExplorerNode(AudioProjectTreeNode node);
34+
void StoreCopiedFromAudioProjectExplorerNode(AudioProjectTreeNode node);
3335
void StoreModdedStatesOnly(bool moddedStatesOnly);
3436
void StoreHircSettings(HircSettings hircSettings);
3537
void StoreAudioFiles(List<AudioFile> audioFiles);
@@ -44,6 +46,7 @@ public class AudioEditorStateService : IAudioEditorStateService
4446
public string AudioProjectFileName { get; set; }
4547
public string AudioProjectFilePath { get; set; }
4648
public AudioProjectTreeNode SelectedAudioProjectExplorerNode { get; set; }
49+
public AudioProjectTreeNode CopiedFromAudioProjectExplorerNode { get; set; }
4750
public bool ShowModdedStatesOnly { get; set; }
4851
public HircSettings HircSettings { get; set; }
4952
public List<AudioFile> AudioFiles { get; set; } = [];
@@ -58,6 +61,8 @@ public class AudioEditorStateService : IAudioEditorStateService
5861

5962
public void StoreSelectedAudioProjectExplorerNode(AudioProjectTreeNode node) => SelectedAudioProjectExplorerNode = node;
6063

64+
public void StoreCopiedFromAudioProjectExplorerNode(AudioProjectTreeNode node) => CopiedFromAudioProjectExplorerNode = node;
65+
6166
public void StoreModdedStatesOnly(bool showModdedStatesOnly) => ShowModdedStatesOnly = showModdedStatesOnly;
6267

6368
public void StoreHircSettings(HircSettings hircSettings) => HircSettings = hircSettings;
@@ -74,6 +79,7 @@ public void Reset()
7479
AudioProjectFileName = null;
7580
AudioProjectFilePath = null;
7681
SelectedAudioProjectExplorerNode = null;
82+
CopiedFromAudioProjectExplorerNode = null;
7783
ShowModdedStatesOnly = false;
7884
HircSettings = null;
7985
AudioFiles.Clear();

Editors/Audio/AudioEditor/Core/AudioProjectMutation/ActionEventService.cs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,8 @@ public void AddActionEvent(string actionEventTypeName, string actionEventName, L
4242
usedSourceIds.UnionWith(languageSourceIds);
4343

4444
var gameSoundBankName = Wh3SoundBankInformation.GetName(Wh3ActionEventInformation.GetSoundBank(actionEventTypeName));
45-
var audioProjectFileNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
46-
var soundBankName = $"{gameSoundBankName}_{audioProjectFileNameWithoutExtension}";
45+
var audioProjectNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
46+
var soundBankName = $"{gameSoundBankName}_{audioProjectNameWithoutExtension}";
4747
var soundBank = _audioEditorStateService.AudioProject.GetSoundBank(soundBankName);
4848

4949
var actionEventType = Wh3ActionEventInformation.GetActionEventType(actionEventTypeName);
@@ -104,8 +104,8 @@ public void RemoveActionEvent(string actionEventNodeName, string actionEventName
104104
{
105105
var audioProject = _audioEditorStateService.AudioProject;
106106
var gameSoundBankName = Wh3SoundBankInformation.GetName(Wh3ActionEventInformation.GetSoundBank(actionEventNodeName));
107-
var audioProjectFileNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
108-
var soundBankName = $"{gameSoundBankName}_{audioProjectFileNameWithoutExtension}";
107+
var audioProjectNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
108+
var soundBankName = $"{gameSoundBankName}_{audioProjectNameWithoutExtension}";
109109

110110
var soundBank = audioProject.GetSoundBank(soundBankName);
111111
var actionEvent = soundBank.GetActionEvent(actionEventName);

Editors/Audio/AudioEditor/Core/AudioProjectMutation/DialogueEventService.cs

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ namespace Editors.Audio.AudioEditor.Core.AudioProjectMutation
1212
{
1313
public interface IDialogueEventService
1414
{
15-
void AddStatePath(string dialogueEventName, List<AudioFile> audioFiles, HircSettings hircSettings, Dictionary<string, string> stateLookupByStateGroup);
15+
void AddStatePath(string dialogueEventName, List<AudioFile> audioFiles, HircSettings hircSettings, List<KeyValuePair<string, string>> statePathList);
1616
bool RemoveStatePath(string dialogueEventName, string statePathName);
1717
}
1818

@@ -22,7 +22,7 @@ public class DialogueEventService(IAudioEditorStateService audioEditorStateServi
2222
private readonly IAudioRepository _audioRepository = audioRepository;
2323
private readonly IStatePathFactory _statePathFactory = statePathFactory;
2424

25-
public void AddStatePath(string dialogueEventName, List<AudioFile> audioFiles, HircSettings hircSettings, Dictionary<string, string> stateLookupByStateGroup)
25+
public void AddStatePath(string dialogueEventName, List<AudioFile> audioFiles, HircSettings hircSettings, List<KeyValuePair<string, string>> statePathList)
2626
{
2727
var usedHircIds = new HashSet<uint>();
2828
var usedSourceIds = new HashSet<uint>();
@@ -41,13 +41,13 @@ public void AddStatePath(string dialogueEventName, List<AudioFile> audioFiles, H
4141
usedSourceIds.UnionWith(languageSourceIds);
4242

4343
var gameSoundBankName = Wh3SoundBankInformation.GetName(Wh3DialogueEventInformation.GetSoundBank(dialogueEventName));
44-
var audioProjectFileNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
45-
var soundBankName = $"{gameSoundBankName}_{audioProjectFileNameWithoutExtension}";
44+
var audioProjectNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
45+
var soundBankName = $"{gameSoundBankName}_{audioProjectNameWithoutExtension}";
4646
var soundBank = _audioEditorStateService.AudioProject.GetSoundBank(soundBankName);
4747

4848
var dialogueEvent = _audioEditorStateService.AudioProject.GetDialogueEvent(dialogueEventName);
4949
var actorMixerId = Wh3DialogueEventInformation.GetActorMixerId(dialogueEvent.Name);
50-
var statePathFactoryResult = _statePathFactory.Create(stateLookupByStateGroup, audioFiles, hircSettings, usedHircIds, usedSourceIds, soundBank.Language, actorMixerId: actorMixerId);
50+
var statePathFactoryResult = _statePathFactory.Create(statePathList, audioFiles, hircSettings, usedHircIds, usedSourceIds, soundBank.Language, actorMixerId: actorMixerId);
5151
dialogueEvent.StatePaths.InsertAlphabetically(statePathFactoryResult.StatePath);
5252

5353
if (statePathFactoryResult.StatePath.TargetHircTypeIsSound())
@@ -88,8 +88,8 @@ public bool RemoveStatePath(string dialogueEventName, string statePathName)
8888
{
8989
var audioProject = _audioEditorStateService.AudioProject;
9090
var gameSoundBankName = Wh3SoundBankInformation.GetName(Wh3DialogueEventInformation.GetSoundBank(dialogueEventName));
91-
var audioProjectFileNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
92-
var soundBankName = $"{gameSoundBankName}_{audioProjectFileNameWithoutExtension}";
91+
var audioProjectNameWithoutExtension = Path.GetFileNameWithoutExtension(_audioEditorStateService.AudioProjectFileName);
92+
var soundBankName = $"{gameSoundBankName}_{audioProjectNameWithoutExtension}";
9393

9494
var soundBank = audioProject.GetSoundBank(soundBankName);
9595

0 commit comments

Comments
 (0)