void FMatineeImportTools::CopyInterpParticleTrack( TSharedRef<ISequencer> Sequencer, UInterpTrackToggle* MatineeToggleTrack, UMovieSceneParticleTrack* ParticleTrack )
{
	const FScopedTransaction Transaction( NSLOCTEXT( "Sequencer", "PasteMatineeParticleTrack", "Paste Matinee particle track" ) );
	bool bSectionCreated = false;

	ParticleTrack->Modify();

	float KeyTime = MatineeToggleTrack->GetKeyframeTime( 0 );
	UMovieSceneParticleSection* Section = Cast<UMovieSceneParticleSection>( MovieSceneHelpers::FindSectionAtTime( ParticleTrack->GetAllSections(), KeyTime ) );
	if ( Section == nullptr )
	{
		Section = Cast<UMovieSceneParticleSection>( ParticleTrack->CreateNewSection() );
		ParticleTrack->AddSection( *Section );
		bSectionCreated = true;
	}

	if (Section->TryModify())
	{
		float SectionMin = Section->GetStartTime();
		float SectionMax = Section->GetEndTime();

		FIntegralCurve& ParticleCurve = Section->GetParticleCurve();
		for ( const auto& Key : MatineeToggleTrack->ToggleTrack )
		{
			EParticleKey::Type ParticleKey;
			if ( TryConvertMatineeToggleToOutParticleKey( Key.ToggleAction, ParticleKey ) )
			{
				ParticleCurve.AddKey( Key.Time, (int32)ParticleKey, ParticleCurve.FindKey( Key.Time ) );
			}
			SectionMin = FMath::Min( SectionMin, Key.Time );
			SectionMax = FMath::Max( SectionMax, Key.Time );
		}

		Section->SetStartTime( SectionMin );
		Section->SetEndTime( SectionMax );

		if ( bSectionCreated )
		{
			Sequencer->NotifyMovieSceneDataChanged();
		}
	}
}
void FMovieSceneParticleTrackInstance::Update( float Position, float LastPosition, const TArray<UObject*>& RuntimeObjects, class IMovieScenePlayer& Player )
{
    // @todo Sequencer We need something analagous to Matinee 1's particle replay tracks
    // What we have here is simple toggling/triggering

    if (Position > LastPosition && Player.GetPlaybackStatus() == EMovieScenePlayerStatus::Playing)
    {
        bool bTrigger = false, bOn = false, bOff = false;

        const TArray<UMovieSceneSection*> Sections = ParticleTrack->GetAllParticleSections();
        for (int32 i = 0; i < Sections.Num(); ++i)
        {
            UMovieSceneParticleSection* Section = Cast<UMovieSceneParticleSection>(Sections[i]);
            if (Section->GetKeyType() == EParticleKey::Trigger)
            {
                if (Position > Section->GetStartTime() && LastPosition < Section->GetStartTime())
                {
                    bTrigger = true;
                }
            }
            else if (Section->GetKeyType() == EParticleKey::Toggle)
            {
                if (Position >= Section->GetStartTime() && Position <= Section->GetEndTime())
                {
                    bOn = true;
                }
                else if (Position >= Section->GetEndTime() && LastPosition < Section->GetEndTime())
                {
                    bOff = true;
                }
            }
        }

        if (bTrigger || bOn || bOff)
        {
            for (int32 i = 0; i < RuntimeObjects.Num(); ++i)
            {
                AEmitter* Emitter = Cast<AEmitter>(RuntimeObjects[i]);
                if (Emitter)
                {
                    if (bTrigger)
                    {
                        Emitter->ToggleActive();
                    }
                    else if (bOn)
                    {
                        Emitter->Activate();
                    }
                    else if (bOff)
                    {
                        Emitter->Deactivate();
                    }
                }
            }
        }
    }
    else
    {
        for (int32 i = 0; i < RuntimeObjects.Num(); ++i)
        {
            AEmitter* Emitter = Cast<AEmitter>(RuntimeObjects[i]);
            if (Emitter)
            {
                Emitter->Deactivate();
            }
        }
    }
}