--- deliantra/Deliantra-Client/bin/cfplus 2007/07/12 19:13:20 1.166
+++ deliantra/Deliantra-Client/bin/cfplus 2007/07/17 16:02:14 1.172
@@ -163,8 +163,10 @@
our $SDL_MIXER;
our $MUSIC_DEFAULT = "in_a_heartbeat.ogg";
our @MUSIC_WANT;
+our $MUSIC_START;
our $MUSIC_PLAYING;
our $MUSIC_PLAYER;
+our $MUSIC_RESUME = 30; # resume music when players less than these many seconds before
our @SOUNDS; # event => file mapping
our %AUDIO_CHUNKS; # audio files
@@ -529,17 +531,25 @@
can_events => 1,
tooltip => "" . (CFPlus::OpenGL::gl_extensions) . "");
+ my $vidmode_tooltip =
+ "Video Mode. The video mode to use for fullscreen (and the window size for windowed operation). "
+ . "The format is width x height \@ depth-per-channel + alpha-channel.";
+
$table->add (0, $row, new CFPlus::UI::Label valign => 0, align => 1, text => "Video Mode");
$table->add (1, $row++, my $hbox = new CFPlus::UI::HBox);
- $hbox->add (my $mode_slider = new CFPlus::UI::Slider force_w => $WIDTH * 0.1, expand => 1, range => [$CFG->{sdl_mode}, 0, $#SDL_MODES, 0, 1]);
- $hbox->add (my $mode_label = new CFPlus::UI::Label align => 0, valign => 0, height => 0.8, template => "9999x9999");
+ $hbox->add (my $mode_slider = new CFPlus::UI::Slider
+ force_w => $WIDTH * 0.1, expand => 1, range => [$CFG->{sdl_mode}, 0, $#SDL_MODES, 0, 1],
+ tooltip => $vidmode_tooltip);
+ $hbox->add (my $mode_label = new CFPlus::UI::Label
+ align => 0, valign => 0, height => 0.8, template => "9999x9999@9+9",
+ can_events => 1, tooltip => $vidmode_tooltip);
$mode_slider->connect (changed => sub {
my ($self, $value) = @_;
$CFG->{sdl_mode} = $self->{range}[0] = $value = int $value;
- $mode_label->set_text (sprintf "%dx%d", @{$SDL_MODES[$value]});
+ $mode_label->set_text (sprintf '%dx%d@%d+%d', @{$SDL_MODES[$value]});
});
$mode_slider->emit (changed => $mode_slider->{range}[0]);
@@ -1280,7 +1290,14 @@
}
sub autopickup_setup {
- my $table = new CFPlus::UI::Table;
+ my $r = new CFPlus::UI::ScrolledWindow (
+ expand => 1,
+ scroll_y => 1
+ );
+ $r->add (my $table = new CFPlus::UI::Table
+ row_expand => [0],
+ col_expand => [0, 1, 0, 1],
+ );
for (
["General", 0, 0,
@@ -1374,7 +1391,7 @@
0
});
- $table
+ $r
}
my %SORT_ORDER = (
@@ -1718,17 +1735,15 @@
}
sub video_init {
- sdl_init;
-
$CFG->{sdl_mode} = 0 if $CFG->{sdl_mode} >= @SDL_MODES;
my ($old_w, $old_h) = ($WIDTH, $HEIGHT);
- ($WIDTH, $HEIGHT) = @{ $SDL_MODES[$CFG->{sdl_mode}] };
+ ($WIDTH, $HEIGHT, my ($rgb, $alpha)) = @{ $SDL_MODES[$CFG->{sdl_mode}] };
$FULLSCREEN = $CFG->{fullscreen};
$FAST = $CFG->{fast};
- CFPlus::SDL_SetVideoMode $WIDTH, $HEIGHT, $FULLSCREEN
+ CFPlus::SDL_SetVideoMode $WIDTH, $HEIGHT, $rgb, $alpha, $FULLSCREEN
or die "SDL_SetVideoMode failed: " . (CFPlus::SDL_GetError) . "\n";
$SDL_ACTIVE = 1;
@@ -2019,26 +2034,41 @@
sub audio_music_set {
my ($songs) = @_;
- my $count = @$songs;
- my @meta;
+ my @want =
+ grep $_,
+ map $CONN->{music_meta}{$_},
+ @$songs;
- for my $name (@$songs) {
- CFPlus::DB::get resmap => $name, sub {
- my ($data) = @_;
-
- if ($data) {
- $data = JSON::XS->new->utf8->decode ($data);
- $data->{path} = CFPlus::DB::path_of $name;
- push @meta, $data;
- }
+ if (@want) {
+ @MUSIC_WANT = @want;
+ &audio_music_changed ();
+ }
+}
- unless (--$count) {
- if (@meta) {
- @MUSIC_WANT = @meta;
- &audio_music_changed ();
- }
- }
- };
+sub audio_music_start {
+ my $path = $MUSIC_PLAYING->{path}
+ or return;
+
+ CFPlus::DB::prefetch_file $path, 1024_000, sub {
+ # music might have changed...
+ $path eq $MUSIC_PLAYING->{path}
+ or return &audio_music_start ();
+
+ $MUSIC_PLAYER = new_from_file CFPlus::MixMusic $path;
+
+ my $NOW = time;
+
+ if ($MUSIC_PLAYING->{stop_time} > $NOW - $MUSIC_RESUME) {
+ my $pos = $MUSIC_PLAYING->{stop_pos};
+ $MUSIC_PLAYER->fade_in_pos (0, 1000, $pos);
+ $MUSIC_START = time - $pos;
+ } else {
+ $MUSIC_PLAYER->play (0);
+ $MUSIC_START = time;
+ }
+
+ delete $MUSIC_PLAYING->{stop_time};
+ delete $MUSIC_PLAYING->{stop_pos};
}
}
@@ -2052,15 +2082,24 @@
return if $MUSIC_PLAYING
&& grep $MUSIC_PLAYING->{path} eq $_->{path}, @MUSIC_WANT;
+ my $NOW = time;
+
if ($MUSIC_PLAYING) {
+ $MUSIC_PLAYING->{stop_time} = $NOW;
+ $MUSIC_PLAYING->{stop_pos} = $NOW - $MUSIC_START;
CFPlus::MixMusic::fade_out 1000;
} else {
- my $music = $MUSIC_WANT [rand @MUSIC_WANT];
+ # sort by stop time, oldest first
+ @MUSIC_WANT = sort { $a->{stop_time} <=> $b->{stop_time} } @MUSIC_WANT;
- $MUSIC_PLAYING = $music;
+ # if the most recently-played piece played very recently,
+ # resume it, else choose the oldest piece for rotation.
+ $MUSIC_PLAYING =
+ $MUSIC_WANT[-1]{stop_time} > $NOW - $MUSIC_RESUME
+ ? $MUSIC_WANT[-1]
+ : $MUSIC_WANT[0];
- $MUSIC_PLAYER = new_from_file CFPlus::MixMusic $music->{path};
- $MUSIC_PLAYER->play (0);
+ audio_music_start;
}
}
@@ -2138,7 +2177,7 @@
$NOW = time;
($SDL_CB{$_->{type}} || sub { warn "unhandled event $_->{type}" })->($_)
- for CFPlus::SDL_PollEvent;
+ for CFPlus::poll_events;
if (%animate_object) {
$_->animate ($LAST_REFRESH - $NOW) for values %animate_object;
@@ -2182,7 +2221,8 @@
},
CFPlus::SDL_ACTIVEEVENT => sub {
# not useful, as APPACTIVE include sonly iconified state, not unmapped
-# printf "active %x %x\n", $_[0]{gain}, $_[0]{state};#d#
+# printf "active %x %x %x\n", $_[0]{gain}, $_[0]{state}, CFPlus::SDL_GetAppState;#d#
+# printf "a %x\n", CFPlus::SDL_GetAppState & CFPlus::SDL_APPACTIVE;#d#
# printf "A\n" if $_[0]{state} & CFPlus::SDL_APPACTIVE;
# printf "K\n" if $_[0]{state} & CFPlus::SDL_APPINPUTFOCUS;
# printf "M\n" if $_[0]{state} & CFPlus::SDL_APPMOUSEFOCUS;
@@ -2273,10 +2313,8 @@
sdl_init;
- @SDL_MODES = reverse
- grep $_->[0] >= 640 && $_->[1] >= 480,
- CFPlus::SDL_ListModes;
-
+ @SDL_MODES = CFPlus::SDL_ListModes 8, 8;
+ @SDL_MODES = CFPlus::SDL_ListModes 5, 0 unless @SDL_MODES;
@SDL_MODES or CFPlus::fatal "Unable to find a usable video mode\n(hardware accelerated opengl fullscreen)";
$CFG->{sdl_mode} = 0 if $CFG->{sdl_mode} > @SDL_MODES;