Make SoundOutput have events

This commit is contained in:
Matt Nadareski
2021-07-04 23:17:30 -07:00
parent b194adc15d
commit be2c704654
4 changed files with 412 additions and 174 deletions

View File

@@ -193,8 +193,6 @@ namespace RedBookPlayer.GUI
if (_digits[i] != null) if (_digits[i] != null)
_digits[i].Source = GetBitmap(digitString[i]); _digits[i].Source = GetBitmap(digitString[i]);
} }
PlayerViewModel?.UpdateView();
}); });
} }
@@ -211,13 +209,19 @@ namespace RedBookPlayer.GUI
await LoadImage(path); await LoadImage(path);
} }
public void PlayButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Playing = true; public void PlayButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Play();
public void PauseButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Playing = false; public void PauseButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Pause();
public void PlayPauseButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Playing = !(PlayerViewModel.Playing ?? false); public void PlayPauseButton_Click(object sender, RoutedEventArgs e)
{
if(PlayerViewModel.Playing == true)
PlayerViewModel.Pause();
else
PlayerViewModel.Play();
}
public void StopButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Playing = null; public void StopButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.Stop();
public void NextTrackButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.NextTrack(); public void NextTrackButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.NextTrack();
@@ -237,11 +241,11 @@ namespace RedBookPlayer.GUI
public void MuteToggleButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.ToggleMute(); public void MuteToggleButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.ToggleMute();
public void EnableDeEmphasisButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.ApplyDeEmphasis = true; public void EnableDeEmphasisButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.SetDeEmphasis(true);
public void DisableDeEmphasisButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.ApplyDeEmphasis = false; public void DisableDeEmphasisButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.SetDeEmphasis(false);
public void EnableDisableDeEmphasisButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.ApplyDeEmphasis = !PlayerViewModel.ApplyDeEmphasis; public void EnableDisableDeEmphasisButton_Click(object sender, RoutedEventArgs e) => PlayerViewModel.SetDeEmphasis(!PlayerViewModel.ApplyDeEmphasis);
#endregion #endregion
} }

View File

@@ -1,7 +1,6 @@
using System.ComponentModel;
using System.Linq; using System.Linq;
using Aaru.CommonTypes.Enums;
using ReactiveUI; using ReactiveUI;
using RedBookPlayer.Discs;
using RedBookPlayer.Hardware; using RedBookPlayer.Hardware;
namespace RedBookPlayer.GUI namespace RedBookPlayer.GUI
@@ -18,7 +17,7 @@ namespace RedBookPlayer.GUI
/// </summary> /// </summary>
private int? _lastVolume = null; private int? _lastVolume = null;
#region Player Status #region Player Passthrough
/// <summary> /// <summary>
/// Indicate if the model is ready to be used /// Indicate if the model is ready to be used
@@ -26,29 +25,12 @@ namespace RedBookPlayer.GUI
public bool Initialized => _player?.Initialized ?? false; public bool Initialized => _player?.Initialized ?? false;
/// <summary> /// <summary>
/// Indicate the player state /// Indicate if the output is playing
/// </summary> /// </summary>
public bool? Playing public bool? Playing
{ {
get => _player?.Playing ?? false; get => _playing;
set private set => this.RaiseAndSetIfChanged(ref _playing, value);
{
if(_player != null)
_player.Playing = value;
}
}
/// <summary>
/// Indicate the current playback volume
/// </summary>
public int Volume
{
get => _player?.Volume ?? 100;
set
{
if(_player != null)
_player.Volume = value;
}
} }
/// <summary> /// <summary>
@@ -56,14 +38,23 @@ namespace RedBookPlayer.GUI
/// </summary> /// </summary>
public bool ApplyDeEmphasis public bool ApplyDeEmphasis
{ {
get => _player?.ApplyDeEmphasis ?? false; get => _applyDeEmphasis;
set private set => this.RaiseAndSetIfChanged(ref _applyDeEmphasis, value);
{
if(_player != null)
_player.ApplyDeEmphasis = value;
}
} }
/// <summary>
/// Current playback volume
/// </summary>
public int Volume
{
get => _volume;
set => this.RaiseAndSetIfChanged(ref _volume, value);
}
private bool? _playing;
private bool _applyDeEmphasis;
private int _volume;
#endregion #endregion
#region Model-Provided Playback Information #region Model-Provided Playback Information
@@ -145,11 +136,29 @@ namespace RedBookPlayer.GUI
// Create and attempt to initialize new Player // Create and attempt to initialize new Player
_player = new Player(path, autoPlay, defaultVolume); _player = new Player(path, autoPlay, defaultVolume);
if(Initialized) if(Initialized)
UpdateView(); {
_player.PropertyChanged += PlayerStateChanged;
PlayerStateChanged(this, null);
}
} }
#region Playback #region Playback
/// <summary>
/// Begin playback
/// </summary>
public void Play() => _player.Play();
/// <summary>
/// Pause current playback
/// </summary>
public void Pause() => _player.Pause();
/// <summary>
/// Stop current playback
/// </summary>
public void Stop() => _player.Stop();
/// <summary> /// <summary>
/// Move to the next playable track /// Move to the next playable track
/// </summary> /// </summary>
@@ -193,7 +202,7 @@ namespace RedBookPlayer.GUI
public string GenerateDigitString() public string GenerateDigitString()
{ {
// If the disc isn't initialized, return all '-' characters // If the disc isn't initialized, return all '-' characters
if(_player?.OpticalDisc == null || !_player.OpticalDisc.Initialized) if(_player?.Initialized != true)
return string.Empty.PadLeft(20, '-'); return string.Empty.PadLeft(20, '-');
// Otherwise, take the current time into account // Otherwise, take the current time into account
@@ -201,24 +210,30 @@ namespace RedBookPlayer.GUI
int[] numbers = new int[] int[] numbers = new int[]
{ {
_player.OpticalDisc.CurrentTrackNumber + 1, _player.CurrentTrackNumber + 1,
_player.OpticalDisc.CurrentTrackIndex, _player.CurrentTrackIndex,
(int)(sectorTime / (75 * 60)), (int)(sectorTime / (75 * 60)),
(int)(sectorTime / 75 % 60), (int)(sectorTime / 75 % 60),
(int)(sectorTime % 75), (int)(sectorTime % 75),
_player.OpticalDisc.TotalTracks, _player.TotalTracks,
_player.OpticalDisc.TotalIndexes, _player.TotalIndexes,
(int)(_player.OpticalDisc.TotalTime / (75 * 60)), (int)(_player.TotalTime / (75 * 60)),
(int)(_player.OpticalDisc.TotalTime / 75 % 60), (int)(_player.TotalTime / 75 % 60),
(int)(_player.OpticalDisc.TotalTime % 75), (int)(_player.TotalTime % 75),
}; };
return string.Join("", numbers.Select(i => i.ToString().PadLeft(2, '0').Substring(0, 2))); return string.Join("", numbers.Select(i => i.ToString().PadLeft(2, '0').Substring(0, 2)));
} }
/// <summary>
/// Set de-emphasis status
/// </summary>
/// <param name="apply"></param>
public void SetDeEmphasis(bool apply) => _player?.SetDeEmphasis(apply);
/// <summary> /// <summary>
/// Temporarily mute playback /// Temporarily mute playback
/// </summary> /// </summary>
@@ -239,30 +254,24 @@ namespace RedBookPlayer.GUI
/// <summary> /// <summary>
/// Update the UI from the internal player /// Update the UI from the internal player
/// </summary> /// </summary>
public void UpdateView() private void PlayerStateChanged(object sender, PropertyChangedEventArgs e)
{ {
if(_player?.Initialized != true) if(_player?.Initialized != true)
return; return;
Playing = _player.Playing;
ApplyDeEmphasis = _player.ApplyDeEmphasis;
Volume = _player.Volume;
CurrentSector = _player.GetCurrentSectorTime(); CurrentSector = _player.GetCurrentSectorTime();
TotalSectors = _player.OpticalDisc.TotalTime; TotalSectors = _player.TotalTime;
HiddenTrack = _player.OpticalDisc.TimeOffset > 150; HiddenTrack = _player.HiddenTrack;
if(_player.OpticalDisc is CompactDisc compactDisc) QuadChannel = _player.QuadChannel;
{ IsDataTrack = _player.IsDataTrack;
QuadChannel = compactDisc.QuadChannel; CopyAllowed = _player.CopyAllowed;
IsDataTrack = compactDisc.IsDataTrack; TrackHasEmphasis = _player.TrackHasEmphasis;
CopyAllowed = compactDisc.CopyAllowed;
TrackHasEmphasis = compactDisc.TrackHasEmphasis;
}
else
{
QuadChannel = false;
IsDataTrack = _player.OpticalDisc.TrackType != TrackType.Audio;
CopyAllowed = false;
TrackHasEmphasis = false;
}
} }
#endregion #endregion

View File

@@ -1,68 +1,141 @@
using System; using System;
using System.ComponentModel;
using System.IO; using System.IO;
using Aaru.CommonTypes.Enums;
using Aaru.DiscImages; using Aaru.DiscImages;
using Aaru.Filters; using Aaru.Filters;
using ReactiveUI;
using RedBookPlayer.Discs; using RedBookPlayer.Discs;
namespace RedBookPlayer.Hardware namespace RedBookPlayer.Hardware
{ {
public class Player public class Player : ReactiveObject
{ {
#region Public Fields
/// <summary> /// <summary>
/// Indicate if the player is ready to be used /// Indicate if the player is ready to be used
/// </summary> /// </summary>
public bool Initialized { get; private set; } = false; public bool Initialized { get; private set; } = false;
/// <summary> #region OpticalDisc Passthrough
/// OpticalDisc object
/// </summary>
public OpticalDisc OpticalDisc { get; private set; }
/// <summary> /// <summary>
/// Indicate if the disc is playing /// Current track number
/// </summary> /// </summary>
public bool? Playing public int CurrentTrackNumber
{ {
get => _soundOutput?.Playing; get => _currentTrackNumber;
set private set => this.RaiseAndSetIfChanged(ref _currentTrackNumber, value);
{
if(OpticalDisc == null || !OpticalDisc.Initialized)
return;
// If the playing state has not changed, do nothing
if(value == _soundOutput?.Playing)
return;
if(value == true)
{
_soundOutput.Play();
OpticalDisc.SetTotalIndexes();
}
else if(value == false)
{
_soundOutput.Stop();
}
else
{
_soundOutput.Stop();
OpticalDisc.LoadFirstTrack();
}
}
} }
/// <summary> /// <summary>
/// Indicate the current playback volume /// Current track index
/// </summary> /// </summary>
public int Volume public ushort CurrentTrackIndex
{ {
get => _soundOutput?.Volume ?? 100; get => _currentTrackIndex;
set private set => this.RaiseAndSetIfChanged(ref _currentTrackIndex, value);
{ }
if(_soundOutput != null)
_soundOutput.Volume = value; /// <summary>
} /// Current sector number
/// </summary>
public ulong CurrentSector
{
get => _currentSector;
private set => this.RaiseAndSetIfChanged(ref _currentSector, value);
}
/// <summary>
/// Represents if the disc has a hidden track
/// </summary>
public bool HiddenTrack
{
get => _hasHiddenTrack;
private set => this.RaiseAndSetIfChanged(ref _hasHiddenTrack, value);
}
/// <summary>
/// Represents the 4CH flag [CompactDisc only]
/// </summary>
public bool QuadChannel
{
get => _quadChannel;
private set => this.RaiseAndSetIfChanged(ref _quadChannel, value);
}
/// <summary>
/// Represents the DATA flag [CompactDisc only]
/// </summary>
public bool IsDataTrack
{
get => _isDataTrack;
private set => this.RaiseAndSetIfChanged(ref _isDataTrack, value);
}
/// <summary>
/// Represents the DCP flag [CompactDisc only]
/// </summary>
public bool CopyAllowed
{
get => _copyAllowed;
private set => this.RaiseAndSetIfChanged(ref _copyAllowed, value);
}
/// <summary>
/// Represents the PRE flag [CompactDisc only]
/// </summary>
public bool TrackHasEmphasis
{
get => _trackHasEmphasis;
private set => this.RaiseAndSetIfChanged(ref _trackHasEmphasis, value);
}
/// <summary>
/// Represents the total tracks on the disc
/// </summary>
public int TotalTracks => _opticalDisc.TotalTracks;
/// <summary>
/// Represents the total indices on the disc
/// </summary>
public int TotalIndexes => _opticalDisc.TotalIndexes;
/// <summary>
/// Total sectors in the image
/// </summary>
public ulong TotalSectors => _opticalDisc.TotalSectors;
/// <summary>
/// Represents the time adjustment offset for the disc
/// </summary>
public ulong TimeOffset => _opticalDisc.TimeOffset;
/// <summary>
/// Represents the total playing time for the disc
/// </summary>
public ulong TotalTime => _opticalDisc.TotalTime;
private int _currentTrackNumber;
private ushort _currentTrackIndex;
private ulong _currentSector;
private bool _hasHiddenTrack;
private bool _quadChannel;
private bool _isDataTrack;
private bool _copyAllowed;
private bool _trackHasEmphasis;
#endregion
#region SoundOutput Passthrough
/// <summary>
/// Indicate if the output is playing
/// </summary>
public bool? Playing
{
get => _playing;
private set => this.RaiseAndSetIfChanged(ref _playing, value);
} }
/// <summary> /// <summary>
@@ -70,10 +143,23 @@ namespace RedBookPlayer.Hardware
/// </summary> /// </summary>
public bool ApplyDeEmphasis public bool ApplyDeEmphasis
{ {
get => _soundOutput?.ApplyDeEmphasis ?? false; get => _applyDeEmphasis;
set => _soundOutput?.SetDeEmphasis(value); private set => this.RaiseAndSetIfChanged(ref _applyDeEmphasis, value);
} }
/// <summary>
/// Current playback volume
/// </summary>
public int Volume
{
get => _volume;
set => this.RaiseAndSetIfChanged(ref _volume, value);
}
private bool? _playing;
private bool _applyDeEmphasis;
private int _volume;
#endregion #endregion
#region Private State Variables #region Private State Variables
@@ -81,7 +167,12 @@ namespace RedBookPlayer.Hardware
/// <summary> /// <summary>
/// Sound output handling class /// Sound output handling class
/// </summary> /// </summary>
public SoundOutput _soundOutput; private readonly SoundOutput _soundOutput;
/// <summary>
/// OpticalDisc object
/// </summary>
private readonly OpticalDisc _opticalDisc;
#endregion #endregion
@@ -96,8 +187,8 @@ namespace RedBookPlayer.Hardware
// Set the internal state for initialization // Set the internal state for initialization
Initialized = false; Initialized = false;
_soundOutput = new SoundOutput(); _soundOutput = new SoundOutput();
_soundOutput.ApplyDeEmphasis = false; _soundOutput.SetDeEmphasis(false);
OpticalDisc = null; _opticalDisc = null;
try try
{ {
@@ -112,7 +203,7 @@ namespace RedBookPlayer.Hardware
image.Open(filter); image.Open(filter);
// Generate and instantiate the disc // Generate and instantiate the disc
OpticalDisc = OpticalDiscFactory.GenerateFromImage(image, autoPlay); _opticalDisc = OpticalDiscFactory.GenerateFromImage(image, autoPlay);
} }
catch catch
{ {
@@ -121,32 +212,88 @@ namespace RedBookPlayer.Hardware
} }
// Initialize the sound output // Initialize the sound output
_soundOutput.Init(OpticalDisc, autoPlay, defaultVolume); _soundOutput.Init(_opticalDisc, autoPlay, defaultVolume);
if(_soundOutput == null || !_soundOutput.Initialized) if(_soundOutput == null || !_soundOutput.Initialized)
return; return;
// Add event handling for the sound output
_soundOutput.PropertyChanged += SoundOutputStateChanged;
// Mark the player as ready // Mark the player as ready
Initialized = true; Initialized = true;
SetDiscInformation();
} }
#region Playback #region Playback
/// <summary>
/// Begin playback
/// </summary>
public void Play()
{
if(_opticalDisc == null || !_opticalDisc.Initialized)
return;
else if(_soundOutput == null)
return;
else if(_soundOutput.Playing)
return;
_soundOutput.Play();
_opticalDisc.SetTotalIndexes();
Playing = true;
}
/// <summary>
/// Pause current playback
/// </summary>
public void Pause()
{
if(_opticalDisc == null || !_opticalDisc.Initialized)
return;
else if(_soundOutput == null)
return;
else if(!_soundOutput.Playing)
return;
_soundOutput?.Stop();
Playing = false;
}
/// <summary>
/// Stop current playback
/// </summary>
public void Stop()
{
if(_opticalDisc == null || !_opticalDisc.Initialized)
return;
else if(_soundOutput == null)
return;
else if(!_soundOutput.Playing)
return;
_soundOutput?.Stop();
_opticalDisc.LoadFirstTrack();
Playing = null;
}
/// <summary> /// <summary>
/// Move to the next playable track /// Move to the next playable track
/// </summary> /// </summary>
public void NextTrack() public void NextTrack()
{ {
if(OpticalDisc == null || !OpticalDisc.Initialized) if(_opticalDisc == null || !_opticalDisc.Initialized)
return; return;
bool? wasPlaying = Playing; bool? wasPlaying = Playing;
if(wasPlaying == true) Playing = false; if(wasPlaying == true) Pause();
OpticalDisc.NextTrack(); _opticalDisc.NextTrack();
if(OpticalDisc is CompactDisc compactDisc) if(_opticalDisc is CompactDisc compactDisc)
_soundOutput.ApplyDeEmphasis = compactDisc.TrackHasEmphasis; _soundOutput.SetDeEmphasis(compactDisc.TrackHasEmphasis);
if(wasPlaying == true) Playing = true; SetDiscInformation();
if(wasPlaying == true) Play();
} }
/// <summary> /// <summary>
@@ -154,17 +301,19 @@ namespace RedBookPlayer.Hardware
/// </summary> /// </summary>
public void PreviousTrack() public void PreviousTrack()
{ {
if(OpticalDisc == null || !OpticalDisc.Initialized) if(_opticalDisc == null || !_opticalDisc.Initialized)
return; return;
bool? wasPlaying = Playing; bool? wasPlaying = Playing;
if(wasPlaying == true) Playing = false; if(wasPlaying == true) Pause();
OpticalDisc.PreviousTrack(); _opticalDisc.PreviousTrack();
if(OpticalDisc is CompactDisc compactDisc) if(_opticalDisc is CompactDisc compactDisc)
_soundOutput.ApplyDeEmphasis = compactDisc.TrackHasEmphasis; _soundOutput.SetDeEmphasis(compactDisc.TrackHasEmphasis);
if(wasPlaying == true) Playing = true; SetDiscInformation();
if(wasPlaying == true) Play();
} }
/// <summary> /// <summary>
@@ -173,17 +322,19 @@ namespace RedBookPlayer.Hardware
/// <param name="changeTrack">True if index changes can trigger a track change, false otherwise</param> /// <param name="changeTrack">True if index changes can trigger a track change, false otherwise</param>
public void NextIndex(bool changeTrack) public void NextIndex(bool changeTrack)
{ {
if(OpticalDisc == null || !OpticalDisc.Initialized) if(_opticalDisc == null || !_opticalDisc.Initialized)
return; return;
bool? wasPlaying = Playing; bool? wasPlaying = Playing;
if(wasPlaying == true) Playing = false; if(wasPlaying == true) Pause();
OpticalDisc.NextIndex(changeTrack); _opticalDisc.NextIndex(changeTrack);
if(OpticalDisc is CompactDisc compactDisc) if(_opticalDisc is CompactDisc compactDisc)
_soundOutput.ApplyDeEmphasis = compactDisc.TrackHasEmphasis; _soundOutput.SetDeEmphasis(compactDisc.TrackHasEmphasis);
if(wasPlaying == true) Playing = true; SetDiscInformation();
if(wasPlaying == true) Play();
} }
/// <summary> /// <summary>
@@ -192,17 +343,19 @@ namespace RedBookPlayer.Hardware
/// <param name="changeTrack">True if index changes can trigger a track change, false otherwise</param> /// <param name="changeTrack">True if index changes can trigger a track change, false otherwise</param>
public void PreviousIndex(bool changeTrack) public void PreviousIndex(bool changeTrack)
{ {
if(OpticalDisc == null || !OpticalDisc.Initialized) if(_opticalDisc == null || !_opticalDisc.Initialized)
return; return;
bool? wasPlaying = Playing; bool? wasPlaying = Playing;
if(wasPlaying == true) Playing = false; if(wasPlaying == true) Pause();
OpticalDisc.PreviousIndex(changeTrack); _opticalDisc.PreviousIndex(changeTrack);
if(OpticalDisc is CompactDisc compactDisc) if(_opticalDisc is CompactDisc compactDisc)
_soundOutput.ApplyDeEmphasis = compactDisc.TrackHasEmphasis; _soundOutput.SetDeEmphasis(compactDisc.TrackHasEmphasis);
if(wasPlaying == true) Playing = true; SetDiscInformation();
if(wasPlaying == true) Play();
} }
/// <summary> /// <summary>
@@ -210,10 +363,11 @@ namespace RedBookPlayer.Hardware
/// </summary> /// </summary>
public void FastForward() public void FastForward()
{ {
if(OpticalDisc == null || !OpticalDisc.Initialized) if(_opticalDisc == null || !_opticalDisc.Initialized)
return; return;
OpticalDisc.CurrentSector = Math.Min(OpticalDisc.TotalSectors, OpticalDisc.CurrentSector + 75); _opticalDisc.CurrentSector = Math.Min(_opticalDisc.TotalSectors, _opticalDisc.CurrentSector + 75);
SetDiscInformation();
} }
/// <summary> /// <summary>
@@ -221,11 +375,13 @@ namespace RedBookPlayer.Hardware
/// </summary> /// </summary>
public void Rewind() public void Rewind()
{ {
if(OpticalDisc == null || !OpticalDisc.Initialized) if(_opticalDisc == null || !_opticalDisc.Initialized)
return; return;
if(OpticalDisc.CurrentSector >= 75) if(_opticalDisc.CurrentSector >= 75)
OpticalDisc.CurrentSector -= 75; _opticalDisc.CurrentSector -= 75;
SetDiscInformation();
} }
#endregion #endregion
@@ -238,21 +394,58 @@ namespace RedBookPlayer.Hardware
/// <returns>ulong representing the current sector time</returns> /// <returns>ulong representing the current sector time</returns>
public ulong GetCurrentSectorTime() public ulong GetCurrentSectorTime()
{ {
ulong sectorTime = OpticalDisc.CurrentSector; ulong sectorTime = _opticalDisc.CurrentSector;
if (OpticalDisc.SectionStartSector != 0) if (_opticalDisc.SectionStartSector != 0)
sectorTime -= OpticalDisc.SectionStartSector; sectorTime -= _opticalDisc.SectionStartSector;
else else
sectorTime += OpticalDisc.TimeOffset; sectorTime += _opticalDisc.TimeOffset;
return sectorTime; return sectorTime;
} }
/// <summary> /// <summary>
/// Set if de-emphasis should be applied /// Set de-emphasis status
/// </summary> /// </summary>
/// <param name="apply">True to enable, false to disable</param> /// <param name="apply"></param>
public void SetDeEmphasis(bool apply) => _soundOutput?.SetDeEmphasis(apply); public void SetDeEmphasis(bool apply) => _soundOutput?.SetDeEmphasis(apply);
/// <summary>
/// Update the player from the current SoundOutput
/// </summary>
private void SoundOutputStateChanged(object sender, PropertyChangedEventArgs e)
{
Playing = _soundOutput.Playing;
ApplyDeEmphasis = _soundOutput.ApplyDeEmphasis;
//Volume = _soundOutput.Volume;
}
/// <summary>
/// Set all current disc information
/// </summary>
private void SetDiscInformation()
{
CurrentTrackNumber = _opticalDisc.CurrentTrackNumber;
CurrentTrackIndex = _opticalDisc.CurrentTrackIndex;
CurrentSector = _opticalDisc.CurrentSector;
HiddenTrack = TimeOffset > 150;
if(_opticalDisc is CompactDisc compactDisc)
{
QuadChannel = compactDisc.QuadChannel;
IsDataTrack = compactDisc.IsDataTrack;
CopyAllowed = compactDisc.CopyAllowed;
TrackHasEmphasis = compactDisc.TrackHasEmphasis;
}
else
{
QuadChannel = false;
IsDataTrack = _opticalDisc.TrackType != TrackType.Audio;
CopyAllowed = false;
TrackHasEmphasis = false;
}
}
#endregion #endregion
} }
} }

View File

@@ -4,11 +4,12 @@ using System.Threading.Tasks;
using CSCore.SoundOut; using CSCore.SoundOut;
using NWaves.Audio; using NWaves.Audio;
using NWaves.Filters.BiQuad; using NWaves.Filters.BiQuad;
using ReactiveUI;
using RedBookPlayer.Discs; using RedBookPlayer.Discs;
namespace RedBookPlayer.Hardware namespace RedBookPlayer.Hardware
{ {
public class SoundOutput public class SoundOutput : ReactiveObject
{ {
#region Public Fields #region Public Fields
@@ -17,15 +18,23 @@ namespace RedBookPlayer.Hardware
/// </summary> /// </summary>
public bool Initialized { get; private set; } = false; public bool Initialized { get; private set; } = false;
/// <summary>
/// Indicates if de-emphasis should be applied
/// </summary>
public bool ApplyDeEmphasis { get; set; } = false;
/// <summary> /// <summary>
/// Indicate if the output is playing /// Indicate if the output is playing
/// </summary> /// </summary>
public bool Playing => _soundOut.PlaybackState == PlaybackState.Playing; public bool Playing
{
get => _playing;
private set => this.RaiseAndSetIfChanged(ref _playing, value);
}
/// <summary>
/// Indicates if de-emphasis should be applied
/// </summary>
public bool ApplyDeEmphasis
{
get => _applyDeEmphasis;
private set => this.RaiseAndSetIfChanged(ref _applyDeEmphasis, value);
}
/// <summary> /// <summary>
/// Current playback volume /// Current playback volume
@@ -35,24 +44,24 @@ namespace RedBookPlayer.Hardware
get => _volume; get => _volume;
set set
{ {
int tempVolume = value;
if(value > 100) if(value > 100)
_volume = 100; tempVolume = 100;
else if(value < 0) else if(value < 0)
_volume = 0; tempVolume = 0;
else
_volume = value; this.RaiseAndSetIfChanged(ref _volume, tempVolume);
} }
} }
private bool _playing;
private bool _applyDeEmphasis;
private int _volume;
#endregion #endregion
#region Private State Variables #region Private State Variables
/// <summary>
/// Current position in the sector
/// </summary>
private int _currentSectorReadPosition = 0;
/// <summary> /// <summary>
/// OpticalDisc from the parent player for easy access /// OpticalDisc from the parent player for easy access
/// </summary> /// </summary>
@@ -61,11 +70,6 @@ namespace RedBookPlayer.Hardware
/// </remarks> /// </remarks>
private OpticalDisc _opticalDisc; private OpticalDisc _opticalDisc;
/// <summary>
/// Internal value for the volume
/// </summary>
private int _volume;
/// <summary> /// <summary>
/// Data provider for sound output /// Data provider for sound output
/// </summary> /// </summary>
@@ -86,6 +90,11 @@ namespace RedBookPlayer.Hardware
/// </summary> /// </summary>
private BiQuadFilter _deEmphasisFilterRight; private BiQuadFilter _deEmphasisFilterRight;
/// <summary>
/// Current position in the sector
/// </summary>
private int _currentSectorReadPosition = 0;
/// <summary> /// <summary>
/// Lock object for reading track data /// Lock object for reading track data
/// </summary> /// </summary>
@@ -254,22 +263,45 @@ namespace RedBookPlayer.Hardware
/// <summary> /// <summary>
/// Start audio playback /// Start audio playback
/// </summary> /// </summary>
public void Play() => _soundOut.Play(); public void Play()
{
if (_soundOut.PlaybackState != PlaybackState.Playing)
_soundOut.Play();
Playing = _soundOut.PlaybackState == PlaybackState.Playing;
}
/// <summary>
/// Pause audio playback
/// </summary>
public void Pause()
{
if(_soundOut.PlaybackState != PlaybackState.Paused)
_soundOut.Pause();
Playing = _soundOut.PlaybackState == PlaybackState.Playing;
}
/// <summary> /// <summary>
/// Stop audio playback /// Stop audio playback
/// </summary> /// </summary>
public void Stop() => _soundOut.Stop(); public void Stop()
{
if(_soundOut.PlaybackState != PlaybackState.Stopped)
_soundOut.Stop();
Playing = _soundOut.PlaybackState == PlaybackState.Playing;
}
#endregion #endregion
#region Helpers #region Helpers
/// <summary> /// <summary>
/// Toggle de-emphasis processing /// Set de-emphasis status
/// </summary> /// </summary>
/// <param name="enable">True to apply de-emphasis, false otherwise</param> /// <param name="apply"></param>
public void SetDeEmphasis(bool enable) => ApplyDeEmphasis = enable; public void SetDeEmphasis(bool apply) => ApplyDeEmphasis = apply;
/// <summary> /// <summary>
/// Sets or resets the de-emphasis filters /// Sets or resets the de-emphasis filters