diff options
Diffstat (limited to 'src/app/xineEngine.cpp')
-rw-r--r-- | src/app/xineEngine.cpp | 43 |
1 files changed, 40 insertions, 3 deletions
diff --git a/src/app/xineEngine.cpp b/src/app/xineEngine.cpp index 74f4f35..3a05862 100644 --- a/src/app/xineEngine.cpp +++ b/src/app/xineEngine.cpp @@ -26,6 +26,7 @@ namespace Codeine { VideoWindow *VideoWindow::s_instance = 0; +bool VideoWindow::s_logarithmicVolume = false; VideoWindow::VideoWindow( TQWidget *parent ) @@ -53,6 +54,13 @@ VideoWindow::VideoWindow( TQWidget *parent ) //TODO sucks //TODO namespace this? myList->next = myList; //init the buffer list + + // Detect xine version, this is used for volume adjustment. + // Xine versions prior to 1.2.13 use linear volume, so the engine uses logarithmic volume. + // Xine versions starting from 1.2.13 use logarithmic volume, so the engine uses linear volume. + int xinemajor = 0, xineminor = 0, xinemaint = 0; + xine_get_version(&xinemajor, &xineminor, &xinemaint); + s_logarithmicVolume = (xinemajor * 1000000 + xineminor * 1000 + xinemaint < 1002013); } VideoWindow::~VideoWindow() @@ -65,7 +73,12 @@ VideoWindow::~VideoWindow() if( m_stream && xine_get_status( m_stream ) == XINE_STATUS_PLAY ) { int cum = 0; for( int v = 99; v >= 0; v-- ) { - xine_set_param( m_stream, XINE_PARAM_AUDIO_AMP_LEVEL, v ); + int vol = v; + if (s_logarithmicVolume) + { + vol = makeVolumeLogarithmic(vol); + } + xine_set_param( m_stream, XINE_PARAM_AUDIO_AMP_LEVEL, vol ); int sleep = int(32000 * (-std::log10( double(v + 1) ) + 2)); ::usleep( sleep ); @@ -255,6 +268,7 @@ VideoWindow::load( const KURL &url ) setParameter( XINE_PARAM_SPU_CHANNEL, -1 ); setParameter( XINE_PARAM_AUDIO_CHANNEL_LOGICAL, -1 ); setParameter( XINE_PARAM_VO_ASPECT_RATIO, 0 ); + // 100 is the same for both linear and logarithmic volume control setParameter( XINE_PARAM_AUDIO_AMP_LEVEL, 100 ); #undef setParameter @@ -445,8 +459,20 @@ VideoWindow::posTimeLength( PosTimeLength type ) const uint VideoWindow::volume() const { - //TODO I don't like the design - return xine_get_param( m_stream, XINE_PARAM_AUDIO_AMP_LEVEL ); + int vol = xine_get_param( m_stream, XINE_PARAM_AUDIO_AMP_LEVEL ); + if (s_logarithmicVolume) + { + vol = 100 - 100.0 * (pow(10, (100.0 - vol) / 100.0) - 1) / 9.0; + } + if (vol < 0) + { + vol = 0; + } + if (vol > 100) + { + vol = 100; + } + return (uint)vol; } void @@ -532,6 +558,13 @@ VideoWindow::seek( uint pos ) xine_set_param( m_stream, XINE_PARAM_AUDIO_AMP_MUTE, 0 ); } +int +VideoWindow::makeVolumeLogarithmic(int volume) +{ + // We're using a logarithmic function to make the volume ramp more natural. + return static_cast<uint>( 100 - 100.0 * std::log10( ( 100 - volume ) * 0.09 + 1.0 ) ); +} + void VideoWindow::setStreamParameter( int value ) { @@ -558,6 +591,10 @@ VideoWindow::setStreamParameter( int value ) { parameter = XINE_PARAM_AUDIO_AMP_LEVEL; value = 100 - value; // TQt sliders are wrong way round when vertical + if (s_logarithmicVolume) + { + value = makeVolumeLogarithmic(value); + } } else return; |