/* * call-seq: * play( options={:fade_in => 0, :repeats => 0, :start_at => 0} ) -> self * * Play the Music, optionally fading in, repeating a certain number * of times (or forever), and/or starting at a certain position in * the song. * * See also #pause and #stop. * * options:: Hash of options, listed below. (Hash, required) * * :fade_in:: Fade in from silence over the given number of * seconds. Default: 0. (Numeric, optional) * :repeats:: Repeat the music the given number of times, or * forever (or until stopped) if -1. Default: 0. * (Integer, optional) * :start_at:: Start playing the music at the given time in the * song, in seconds. Default: 0. (Numeric, optional) * **NOTE**: Non-zero start times only work for * OGG and MP3 formats! Please refer to #jump. * * * Returns:: The receiver (self). * May raise:: SDLError, if the music file could not be played, or * if you used :start_at with an unsupported format. * * **NOTE**: Only one music can be playing at once. If any music is * already playing (or paused), it will be stopped before playing the * new music. * * Example: * # Fade in over 2 seconds, play 4 times (1 + 3 repeats), * # starting at 60 seconds since the beginning of the song. * music.play( :fade_in => 2, :repeats => 3, :start_at => 60 ); * */ static VALUE rg_music_play( int argc, VALUE *argv, VALUE self ) { RG_Music *music; Data_Get_Struct(self, RG_Music, music); VALUE options; rb_scan_args(argc, argv, "01", &options); int fade_in = 0; int repeats = 1; double start_at = 0; /* If we got some options */ if( RTEST(options) ) { /* Make sure options is a Hash table */ if( TYPE(options) != T_HASH ) { rb_raise(rb_eTypeError, "wrong argument type %s (expected Hash)", rb_obj_classname(options)); } VALUE temp; temp = rb_hash_aref(options, make_symbol("fade_in")); if( RTEST(temp) ) { fade_in = (int)(1000 * NUM2DBL( temp )); if( fade_in < 0 ) { rb_raise(rb_eArgError, ":fade_in cannot be negative (got %.2f)", fade_in / 1000); } else if( fade_in < 50 ) { /* Work-around for a bug with SDL_mixer not working with small non-zero fade-ins */ fade_in = 0; } } temp = rb_hash_aref(options, make_symbol("repeats")); if( RTEST(temp) ) { repeats = NUM2INT(temp); if( repeats > -1 ) { /* Adjust so repeats means the same as it does for Sound */ repeats += 1; } if( repeats < -1 ) { rb_raise(rb_eArgError, ":repeats cannot be negative, except -1 (got %d)", repeats); } } temp = rb_hash_aref(options, make_symbol("start_at")); if( RTEST(temp) ) { start_at = (double)(NUM2DBL( temp )); if( start_at < 0 ) { rb_raise(rb_eArgError, ":start_at cannot be negative (got %.2f)", start_at); } } } int result = _rg_music_play( music, fade_in, repeats, start_at ); if( result == -1 ) { rb_raise(eSDLError, "Could not play Music: %s", Mix_GetError()); } /* This music is now current. */ _rg_music_set_current( self ); return self; }