Jam-Teacher/Plugins/FMODStudio/Source/FMODStudioEditor/Private/Sequencer/FMODEventParameterTrackEditor.cpp
2020-08-01 13:48:17 +02:00

156 lines
6.8 KiB
C++

// Copyright (c), Firelight Technologies Pty, Ltd. 2012-2020.
#include "FMODEventParameterTrackEditor.h"
#include "FMODAmbientSound.h"
#include "FMODEvent.h"
#include "FMODStudioModule.h"
#include "Framework/MultiBox/MultiBoxBuilder.h"
#include "Sequencer/FMODEventParameterTrack.h"
#include "Sections/MovieSceneParameterSection.h"
#include "Sequencer/FMODParameterSection.h"
#include "SequencerUtilities.h"
#include "fmod_studio.hpp"
#define LOCTEXT_NAMESPACE "FMODEeventParameterTrackEditor"
FName FFMODEventParameterTrackEditor::TrackName("FMODEventParameter");
FFMODEventParameterTrackEditor::FFMODEventParameterTrackEditor(TSharedRef<ISequencer> InSequencer)
: FMovieSceneTrackEditor(InSequencer)
{
}
TSharedRef<ISequencerTrackEditor> FFMODEventParameterTrackEditor::CreateTrackEditor(TSharedRef<ISequencer> OwningSequencer)
{
return MakeShareable(new FFMODEventParameterTrackEditor(OwningSequencer));
}
TSharedRef<ISequencerSection> FFMODEventParameterTrackEditor::MakeSectionInterface(
UMovieSceneSection &SectionObject, UMovieSceneTrack &Track, FGuid ObjectBinding)
{
UMovieSceneParameterSection *ParameterSection = Cast<UMovieSceneParameterSection>(&SectionObject);
checkf(ParameterSection != nullptr, TEXT("Unsupported section type."));
return MakeShareable(new FFMODParameterSection(*ParameterSection));
}
TSharedPtr<SWidget> FFMODEventParameterTrackEditor::BuildOutlinerEditWidget(
const FGuid &ObjectBinding, UMovieSceneTrack *Track, const FBuildEditWidgetParams &Params)
{
UFMODEventParameterTrack *EventParameterTrack = Cast<UFMODEventParameterTrack>(Track);
// Create a container edit box
return FSequencerUtilities::MakeAddButton(LOCTEXT("ParameterText", "Parameter"),
FOnGetContent::CreateSP(this, &FFMODEventParameterTrackEditor::OnGetAddParameterMenuContent, ObjectBinding, EventParameterTrack),
Params.NodeIsHovered,
GetSequencer());
}
void FFMODEventParameterTrackEditor::BuildObjectBindingTrackMenu(FMenuBuilder &MenuBuilder, const TArray<FGuid> &ObjectBindings, const UClass *ObjectClass)
{
if (ObjectClass->IsChildOf(AFMODAmbientSound::StaticClass()) || ObjectClass->IsChildOf(UFMODAudioComponent::StaticClass()))
{
const TSharedPtr<ISequencer> ParentSequencer = GetSequencer();
MenuBuilder.AddMenuEntry(LOCTEXT("AddFMODParameterTrack", "FMOD Event Parameter Track"),
LOCTEXT("AddFMODParameterTrackTooltip", "Adds a track for controlling FMOD event parameter values."), FSlateIcon(),
FUIAction(FExecuteAction::CreateSP(this, &FFMODEventParameterTrackEditor::AddEventParameterTrack, ObjectBindings[0]),
FCanExecuteAction::CreateSP(this, &FFMODEventParameterTrackEditor::CanAddEventParameterTrack, ObjectBindings[0])));
}
}
bool FFMODEventParameterTrackEditor::SupportsType(TSubclassOf<UMovieSceneTrack> Type) const
{
return Type == UFMODEventParameterTrack::StaticClass();
}
TSharedRef<SWidget> FFMODEventParameterTrackEditor::OnGetAddParameterMenuContent(FGuid ObjectBinding, UFMODEventParameterTrack *EventParameterTrack)
{
TSharedPtr<ISequencer> SequencerPtr = GetSequencer();
AFMODAmbientSound *Sound = SequencerPtr.IsValid() ? Cast<AFMODAmbientSound>(SequencerPtr->FindSpawnedObjectOrTemplate(ObjectBinding)) : nullptr;
UFMODAudioComponent *AudioComponent;
if (IsValid(Sound))
{
AudioComponent = Sound->AudioComponent;
}
else
{
AudioComponent = SequencerPtr.IsValid() ? Cast<UFMODAudioComponent>(SequencerPtr->FindSpawnedObjectOrTemplate(ObjectBinding)) : nullptr;
}
return BuildParameterMenu(ObjectBinding, EventParameterTrack, AudioComponent);
}
TSharedRef<SWidget> FFMODEventParameterTrackEditor::BuildParameterMenu(
FGuid ObjectBinding, UFMODEventParameterTrack *EventParameterTrack, UFMODAudioComponent *AudioComponent)
{
FMenuBuilder AddParameterMenuBuilder(true, nullptr);
if (IsValid(AudioComponent) && AudioComponent->Event.IsValid())
{
TArray<FParameterNameAndAction> ParameterNamesAndActions;
TArray<FMOD_STUDIO_PARAMETER_DESCRIPTION> ParameterDescriptions;
AudioComponent->Event->GetParameterDescriptions(ParameterDescriptions);
for (FMOD_STUDIO_PARAMETER_DESCRIPTION &ParameterDescription : ParameterDescriptions)
{
FName ParameterName(ParameterDescription.name);
FExecuteAction InitAction =
FExecuteAction::CreateSP(this, &FFMODEventParameterTrackEditor::AddParameter, ObjectBinding, EventParameterTrack, ParameterName);
FUIAction AddParameterMenuAction(InitAction);
FParameterNameAndAction NameAndAction(ParameterName, AddParameterMenuAction);
ParameterNamesAndActions.Add(NameAndAction);
}
// Sort and generate menu.
ParameterNamesAndActions.Sort();
for (FParameterNameAndAction NameAndAction : ParameterNamesAndActions)
{
AddParameterMenuBuilder.AddMenuEntry(FText::FromName(NameAndAction.ParameterName), FText(), FSlateIcon(), NameAndAction.Action);
}
}
return AddParameterMenuBuilder.MakeWidget();
}
bool FFMODEventParameterTrackEditor::CanAddEventParameterTrack(FGuid ObjectBinding)
{
return GetSequencer()->GetFocusedMovieSceneSequence()->GetMovieScene()->FindTrack(
UFMODEventParameterTrack::StaticClass(), ObjectBinding, TrackName) == nullptr;
}
void FFMODEventParameterTrackEditor::AddEventParameterTrack(FGuid ObjectBinding)
{
FindOrCreateTrackForObject(ObjectBinding, UFMODEventParameterTrack::StaticClass(), TrackName, true);
GetSequencer()->NotifyMovieSceneDataChanged(EMovieSceneDataChangeType::MovieSceneStructureItemAdded);
}
void FFMODEventParameterTrackEditor::AddParameter(FGuid ObjectBinding, UFMODEventParameterTrack *EventParameterTrack, FName ParameterName)
{
UMovieSceneSequence *MovieSceneSequence = GetMovieSceneSequence();
FFrameNumber KeyTime = GetTimeForKey();
for (TWeakObjectPtr<> Object : GetSequencer()->FindObjectsInCurrentSequence(ObjectBinding))
{
AFMODAmbientSound *Sound = Cast<AFMODAmbientSound>(Object.Get());
UFMODAudioComponent *AudioComponent = nullptr;
if (IsValid(Sound))
{
AudioComponent = Sound->AudioComponent;
}
else
{
AudioComponent = Cast<UFMODAudioComponent>(Object.Get());
}
if (IsValid(AudioComponent))
{
float Value = AudioComponent->GetParameter(ParameterName);
const FScopedTransaction Transaction(LOCTEXT("AddEventParameter", "Add event parameter"));
EventParameterTrack->Modify();
EventParameterTrack->AddParameterKey(ParameterName, KeyTime, Value);
}
}
GetSequencer()->NotifyMovieSceneDataChanged(EMovieSceneDataChangeType::MovieSceneStructureItemAdded);
}
#undef LOCTEXT_NAMESPACE