/t/mixer_effects.t

http://github.com/PerlGameDev/SDL · Perl · 240 lines · 208 code · 31 blank · 1 comment · 11 complexity · f789954287712521c2024dd9cb8c8be9 MD5 · raw file

  1. #!/usr/bin/perl -w
  2. use strict;
  3. use warnings;
  4. use SDL;
  5. use SDL::Config;
  6. my $audiodriver;
  7. BEGIN {
  8. use Config;
  9. if ( !$Config{'useithreads'} ) {
  10. print("1..0 # Skip: Perl not compiled with 'useithreads'\n");
  11. exit(0);
  12. }
  13. require threads;
  14. require threads::shared;
  15. use Test::More;
  16. use lib 't/lib';
  17. use SDL::TestTool;
  18. $audiodriver = $ENV{SDL_AUDIODRIVER};
  19. $ENV{SDL_AUDIODRIVER} = 'dummy' unless $ENV{SDL_RELEASE_TESTING};
  20. if ( !SDL::TestTool->init(SDL_INIT_AUDIO) ) {
  21. plan( skip_all => 'Failed to init sound' );
  22. } elsif ( !SDL::Config->has('SDL_mixer') ) {
  23. plan( skip_all => 'SDL_mixer support not compiled' );
  24. }
  25. }
  26. use SDL::Mixer;
  27. use SDL::Mixer::Channels;
  28. use SDL::Mixer::Effects;
  29. use SDL::Mixer::Samples;
  30. my $can_open = SDL::Mixer::open_audio( 44100, SDL::Audio::AUDIO_S16SYS, 2, 4096 );
  31. unless($can_open == 0)
  32. {
  33. plan( skip_all => 'Cannot open audio :'.SDL::get_error() );
  34. }
  35. is( $can_open ,
  36. 0, '[open_audio] ran'
  37. );
  38. my $delay = 500;
  39. my $audio_test_file = 'test/data/silence.wav';
  40. SDL::Mixer::Channels::volume( -1, 1 );
  41. if ( $ENV{'SDL_RELEASE_TESTING'} ) {
  42. SDL::Mixer::Channels::volume( -1, 20 );
  43. $delay = 1000;
  44. $audio_test_file = 'test/data/sample.wav';
  45. }
  46. my $effect_func_called : shared = 0;
  47. my $effect_done_called : shared = 0;
  48. my @last_stream = ();
  49. sub echo_effect_func {
  50. my $channel = shift;
  51. my $samples = shift;
  52. my $position = shift;
  53. my @stream = @_;
  54. $effect_func_called++;
  55. printf(
  56. "[effect_func] callback: channel=%2s, position=%8s, samples=%6s\n",
  57. $channel, $position, scalar(@stream)
  58. );
  59. my @stream2 = @stream;
  60. my $offset = $samples / 2;
  61. for ( my $i = 0; $i < $samples; $i += 2 ) {
  62. if ( $i < $offset ) {
  63. if ( scalar(@last_stream) == $samples ) {
  64. $stream2[$i] = $stream[$i] * 0.6 + $last_stream[ $samples + $i - $offset ] * 0.4; # left
  65. $stream2[ $i + 1 ] =
  66. $stream[ $i + 1 ] * 0.6 + $last_stream[ $samples + $i - $offset + 1 ] * 0.4; # right
  67. }
  68. } else {
  69. $stream2[$i] = $stream[$i] * 0.6 + $stream[ $i - $offset ] * 0.4; # left
  70. $stream2[ $i + 1 ] = $stream[ $i + 1 ] * 0.6 + $stream[ $i - $offset + 1 ] * 0.4; # right
  71. }
  72. }
  73. @last_stream = @stream;
  74. push( @stream2, $position + $samples );
  75. return @stream2;
  76. }
  77. sub echo_effect_func2 {
  78. my $channel = shift;
  79. my $samples = shift;
  80. my $position = shift;
  81. my @stream = @_;
  82. $effect_func_called++;
  83. printf(
  84. "[effect_func2] callback: channel=%2s, position=%8s, samples=%6s\n",
  85. $channel, $position, scalar(@stream)
  86. );
  87. push( @stream, $position + $samples );
  88. return @stream;
  89. }
  90. sub effect_done2 {
  91. printf("[effect_done2] called\n");
  92. $effect_done_called++;
  93. }
  94. sub effect_done {
  95. printf("[effect_done] called\n");
  96. $effect_done_called++;
  97. }
  98. my $sample_chunk = SDL::Mixer::Samples::load_WAV($audio_test_file);
  99. my $playing_channel = SDL::Mixer::Channels::play_channel( -1, $sample_chunk, -1 );
  100. is( $playing_channel >= 0, 1, "[play_channel] playing $audio_test_file" );
  101. SDL::delay($delay);
  102. my $effect_id = SDL::Mixer::Effects::register(
  103. $playing_channel, "main::echo_effect_func2",
  104. "main::effect_done2", 0
  105. );
  106. isnt( $effect_id, -1, '[register] registerering echo effect callback' );
  107. SDL::delay($delay);
  108. my $check = SDL::Mixer::Effects::unregister( $playing_channel, $effect_id );
  109. isnt(
  110. $check, 0,
  111. '[unregister] unregistering effect_func will call effect_done'
  112. );
  113. SDL::delay(200);
  114. is( $effect_func_called > 0,
  115. 1, "[effect_func] called $effect_func_called times"
  116. );
  117. is( $effect_done_called > 0,
  118. 1, "[effect_done] called $effect_done_called times"
  119. );
  120. SDL::delay($delay);
  121. $effect_func_called = 0;
  122. $effect_done_called = 0;
  123. $effect_id = SDL::Mixer::Effects::register(
  124. $playing_channel, "main::echo_effect_func2",
  125. "main::effect_done2", 0
  126. );
  127. isnt( $effect_id, -1, '[register] registerering echo effect callback' );
  128. SDL::delay($delay);
  129. $check = SDL::Mixer::Effects::unregister( $playing_channel, $effect_id );
  130. isnt(
  131. $check, 0,
  132. '[unregister] unregistering effect_func will call effect_done'
  133. );
  134. SDL::delay(200);
  135. is( $effect_func_called > 0,
  136. 1, "[effect_func] called $effect_func_called times"
  137. );
  138. is( $effect_done_called > 0,
  139. 1, "[effect_done] called $effect_done_called times"
  140. );
  141. $effect_func_called = 0;
  142. $effect_done_called = 0;
  143. my $effect_id_all = SDL::Mixer::Effects::register( MIX_CHANNEL_POST, "main::echo_effect_func",
  144. "main::effect_done", 0
  145. );
  146. isnt( $effect_id_all, -1, '[register] registerering echo effect callback' );
  147. SDL::delay($delay);
  148. isnt(
  149. SDL::Mixer::Effects::unregister_all(MIX_CHANNEL_POST),
  150. 0, '[unregister_all] unregistering all will call effect_done'
  151. );
  152. SDL::delay(200);
  153. is( $effect_func_called > 0,
  154. 1, "[effect_func] called $effect_func_called times"
  155. );
  156. is( $effect_done_called > 0,
  157. 1, "[effect_done] called $effect_done_called times"
  158. );
  159. $effect_func_called = 0;
  160. is( SDL::Mixer::Effects::set_post_mix( "main::echo_effect_func", 0 ),
  161. undef, '[set_post_mix] registering echo effect callback'
  162. );
  163. SDL::delay($delay);
  164. is( SDL::Mixer::Effects::set_post_mix(),
  165. undef, '[set_post_mix] unregistering echo effect callback'
  166. );
  167. SDL::delay(200);
  168. is( $effect_func_called > 0,
  169. 1, "[effect_func] called $effect_func_called times"
  170. );
  171. SDL::delay($delay);
  172. isnt(
  173. SDL::Mixer::Effects::set_panning( $playing_channel, 128, 255 ),
  174. 0, '[set_panning] 50% left, 100% right'
  175. );
  176. SDL::delay($delay);
  177. isnt(
  178. SDL::Mixer::Effects::set_position( $playing_channel, 225, 80 ),
  179. 0, '[set_position] left-behind, 33% away'
  180. );
  181. SDL::delay($delay);
  182. isnt(
  183. SDL::Mixer::Effects::set_distance( $playing_channel, 160 ),
  184. 0, '[set_distance] 66% away'
  185. );
  186. SDL::delay($delay);
  187. isnt(
  188. SDL::Mixer::Effects::set_position( $playing_channel, 0, 0 ),
  189. 0, '[set_position] front, 0% away'
  190. );
  191. SDL::delay($delay);
  192. isnt(
  193. SDL::Mixer::Effects::set_reverse_stereo( $playing_channel, 1 ),
  194. 0, '[set_reverse_stereo] on'
  195. );
  196. SDL::delay($delay);
  197. isnt(
  198. SDL::Mixer::Effects::set_reverse_stereo( $playing_channel, 0 ),
  199. 0, '[set_reverse_stereo] off'
  200. );
  201. SDL::delay($delay);
  202. SDL::Mixer::close_audio();
  203. pass '[close_audio] ran';
  204. if ($audiodriver) {
  205. $ENV{SDL_AUDIODRIVER} = $audiodriver;
  206. } else {
  207. delete $ENV{SDL_AUDIODRIVER};
  208. }
  209. done_testing();