// Fill out your copyright notice in the Description page of Project Settings.

#pragma once

#include "CoreMinimal.h"
#include "Engine/DataAsset.h"
#include "MusicPlaylistDataAsset.generated.h"

class USoundBase;

/**
 * Une liste de morceaux et la facon de les enchainer.
 *
 * DataAsset et pas une variable sur un acteur : c'est de la DONNEE, au meme titre
 * qu'un UItemDataAsset. On en cree autant qu'on veut (menu, exploration, nuit,
 * combat) sans toucher au code, et la meme playlist peut etre referencee par
 * plusieurs maps -- ce qui est exactement ce qui permet au menu et au jeu de
 * partager une musique qui ne se coupe pas entre les deux.
 *
 * Aucun etat ici : l'index en cours, l'ordre tire au sort et le volume vivent
 * dans UMusicSubsystem. Un DataAsset est partage par toutes les references, y
 * mettre de l'etat le partagerait aussi.
 */
UCLASS(BlueprintType)
class EMBERWILD_API UMusicPlaylistDataAsset : public UPrimaryDataAsset
{
	GENERATED_BODY()

public:
	/** Nom lisible, pour un futur affichage "en cours de lecture". */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist")
	FText DisplayName;

	/**
	 * Les morceaux, dans l'ordre de lecture quand l'aleatoire est desactive.
	 *
	 * Les cases vides sont ignorees a la lecture : une reference oubliee ne coupe
	 * pas la musique, elle est simplement sautee.
	 *
	 * IMPORTANT : aucun de ces sons ne doit boucler sur lui-meme (ni "Looping" sur
	 * la SoundWave, ni un noeud Looping dans la SoundCue). L'enchainement repose
	 * sur OnAudioFinished, qui n'est jamais diffuse par un son qui boucle.
	 */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist")
	TArray<TObjectPtr<USoundBase>> Tracks;

	/**
	 * Mode par defaut au demarrage de CETTE playlist.
	 *
	 * Le joueur peut ensuite basculer en cours de route via
	 * UMusicSubsystem::SetShuffleEnabled ; cette valeur n'est relue qu'au
	 * prochain demarrage de playlist.
	 */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist")
	bool bShuffle = true;

	/** Faux = la musique s'arrete quand tous les morceaux ont ete joues une fois. */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist")
	bool bLoop = true;

	/**
	 * Silence entre deux morceaux, tire au hasard dans l'intervalle.
	 *
	 * Une musique d'ambiance qui respire quelques secondes se remarque beaucoup
	 * moins qu'un flux continu, et c'est ce qui evite la lassitude sur une longue
	 * session. A zero, l'enchainement est immediat.
	 */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist", meta = (ClampMin = "0.0", Units = "s"))
	float MinGapBetweenTracks = 0.f;

	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist", meta = (ClampMin = "0.0", Units = "s"))
	float MaxGapBetweenTracks = 0.f;

	/** Correction de niveau propre a cette playlist, par-dessus le volume joueur. */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist", meta = (ClampMin = "0.0", ClampMax = "2.0"))
	float VolumeMultiplier = 1.f;

	/** Fondu entrant au demarrage de la playlist (pas entre deux morceaux). */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist", meta = (ClampMin = "0.0", Units = "s"))
	float FadeInDuration = 2.f;

	/** Fondu sortant quand une autre playlist prend la main, ou a l'arret. */
	UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Playlist", meta = (ClampMin = "0.0", Units = "s"))
	float FadeOutDuration = 2.f;
};
