8 use Time::HiRes qw(gettimeofday);
9 use Glib qw(TRUE FALSE);
12 our $SEMAPHORE_STEP = 1000;
15 my ($class, $args) = @_;
19 $self->{gui} = $args->{gui} or croak;
20 $self->{race_running} = 0;
21 $self->{lap_counting_up} = 1;
26 $self->{cars}->[$i] = SCX::Car->new({
31 $self->car($i)->set_order($i);
37 sub car { return shift->{cars}->[shift]; }
42 return if $self->{race_running} || $self->{start_in_progress}
43 || $self->{qualification_running};
45 $self->{race_running} = 0;
46 $self->{start_in_progress} = 1;
47 $self->{semaphore} = 0;
48 $self->{gui}->show_semaphore(0);
49 Glib::Timeout->add($SEMAPHORE_STEP, \&semaphore_step, $self);
55 return FALSE if !$self->{start_in_progress} && !$self->{race_running};
58 if ($self->{semaphore} <= 5) {
59 $self->{gui}->show_semaphore($self->{semaphore});
60 my $timeout = $SEMAPHORE_STEP;
61 $timeout += $SEMAPHORE_STEP * rand()
62 if $self->{semaphore} == 5;
63 Glib::Timeout->add($timeout, \&semaphore_step, $self);
64 } elsif ($self->{semaphore} == 6) {
65 $self->{race_running} = 1;
66 $self->{race_running_since} = gettimeofday;
67 $self->{start_in_progress} = undef;
68 $self->{gui}->show_semaphore(0);
69 Glib::Timeout->add($SEMAPHORE_STEP, \&semaphore_step, $self);
71 $self->{gui}->show_semaphore(undef);
72 $self->{semaphore} = undef;
79 $self->{race_running} = 0;
83 my ($self, $rounds) = @_;
87 $self->{race_rounds} = $rounds;
89 $self->{race_rounds} = 0;
93 $self->{best_lap} = undef;
95 $self->{gui}->show_semaphore(undef);
96 $self->{race_running} = 0;
97 $self->{start_in_progress} = 0;
99 $self->{gui}->time(undef);
100 $self->{gui}->best_lap(undef);
106 $self->{race_running} = 0;
107 $self->{start_in_progress} = 0;
108 $self->{best_lap} = undef;
112 $self->{gui}->best_lap(undef);
113 $self->{gui}->time(undef);
116 $self->car($car)->reset;
123 $self->{gui}->rounds($self->{qualification_running}
125 : $self->{race_rounds}
126 ? $self->{round} . '/' . $self->{race_rounds}
132 my ($self, $time, $who) = @_;
134 return if !defined $time || $time == 0;
136 # print "Check_best_lap $time $who vs ",
137 # defined $self->{best_lap} ? $self->{best_lap} : 'undef',
139 if (!defined $self->{best_lap}
140 || $time < $self->{best_lap}) {
141 $self->{best_lap} = $time;
142 $self->{gui}->best_lap($time, $who);
148 sub qualification_start {
151 return if $self->{qualification_running};
153 $self->car($car)->set_lap(undef);
154 $self->car($car)->set_laptime(undef);
157 $self->{qualification_running} = 1;
158 $self->{gui}->rounds('Qualification');
159 $self->{gui}->time(undef);
160 $self->{gui}->best_lap(undef);
163 sub packet_received {
164 my ($self, $time) = @_;
166 if ($self->{race_running}) {
167 $self->{gui}->time($time - $self->{race_running_since});
172 my ($self, $now) = @_;
174 return if !$self->{race_running};
179 $laps[$id] = $self->car($id)->{lap} // -1;
180 $times[$id] = $self->car($id)->{first_finish_time} // $now;
183 my @new_order = sort {
184 $laps[$b] <=> $laps[$a]
186 $times[$a] <=> $times[$b]
191 my $lap_max = $laps[$new_order[0]];
192 if (defined $lap_max && $self->{round} && $lap_max != $self->{round}
193 && (!$self->{race_rounds}
194 || $lap_max <= $self->{race_rounds})) {
195 $self->{round} = $lap_max;
200 my $car = $new_order[$id];
201 if ($self->car($car)->{order} != $id) {
202 $self->car($car)->set_order($id);
205 return ($new_order[0], $lap_max, $times[$new_order[0]]);
209 my ($self, $time, $regular, @cars) = @_;
214 for my $car (@cars) {
215 if ($self->car($car)->finish_line($time, $regular)) {
216 $processed{$car} = 1;
222 if ($was_processed) {
223 my ($first_car, $lap_max, $time_min)
224 = $self->recalc_order($time);
227 if ($processed{$car}) {
228 $self->car($car)->recalc_distance(
232 #$self->car($car)->greyout_distance;