mirror of
https://github.com/TomHarte/CLK.git
synced 2025-01-26 15:32:04 +00:00
Attempted to reintroduce the ball.
This commit is contained in:
parent
53cd125712
commit
e00339ef0a
@ -272,6 +272,8 @@ void TIA::set_playfield_control_and_ball_size(uint8_t value)
|
|||||||
playfield_priority_ = PlayfieldPriority::OnTop;
|
playfield_priority_ = PlayfieldPriority::OnTop;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ball_.size = 1 << ((value >> 4)&3);
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::set_playfield_ball_colour(uint8_t colour)
|
void TIA::set_playfield_ball_colour(uint8_t colour)
|
||||||
@ -308,6 +310,7 @@ void TIA::set_player_graphic(int player, uint8_t value)
|
|||||||
{
|
{
|
||||||
player_[player].graphic[1] = value;
|
player_[player].graphic[1] = value;
|
||||||
player_[player^1].graphic[0] = player_[player^1].graphic[1];
|
player_[player^1].graphic[0] = player_[player^1].graphic[1];
|
||||||
|
if(player) ball_.enabled[0] = ball_.enabled[1];
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::set_player_reflected(int player, bool reflected)
|
void TIA::set_player_reflected(int player, bool reflected)
|
||||||
@ -358,18 +361,25 @@ void TIA::set_missile_motion(int missile, uint8_t motion)
|
|||||||
|
|
||||||
void TIA::set_ball_enable(bool enabled)
|
void TIA::set_ball_enable(bool enabled)
|
||||||
{
|
{
|
||||||
|
ball_.enabled[1] = enabled;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::set_ball_delay(bool delay)
|
void TIA::set_ball_delay(bool delay)
|
||||||
{
|
{
|
||||||
|
ball_.enabled_index = delay ? 0 : 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::set_ball_position()
|
void TIA::set_ball_position()
|
||||||
{
|
{
|
||||||
|
position_[(int)MotionIndex::Ball] = 0;
|
||||||
|
|
||||||
|
// setting the ball position also triggers a draw
|
||||||
|
ball_.pixel_position = ball_.size;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::set_ball_motion(uint8_t motion)
|
void TIA::set_ball_motion(uint8_t motion)
|
||||||
{
|
{
|
||||||
|
motion_[(int)MotionIndex::Ball] = (motion >> 4) & 0xf;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::move()
|
void TIA::move()
|
||||||
@ -763,8 +773,93 @@ void TIA::draw_missile_visible(Missile &missile, CollisionType collision_identit
|
|||||||
|
|
||||||
void TIA::draw_ball(int start, int end)
|
void TIA::draw_ball(int start, int end)
|
||||||
{
|
{
|
||||||
|
int first_pixel = first_pixel_cycle - 4 + (horizontal_blank_extend_ ? 8 : 0);
|
||||||
|
|
||||||
|
// movement works across the entire screen, so do work that falls outside of the pixel area
|
||||||
|
if(start < first_pixel)
|
||||||
|
{
|
||||||
|
ball_.pixel_position = std::max(0, ball_.pixel_position - perform_border_motion((int)MotionIndex::Ball, start, std::max(end, first_pixel)));
|
||||||
|
}
|
||||||
|
|
||||||
|
// don't continue to do any drawing if this window ends too early
|
||||||
|
if(end < first_pixel) return;
|
||||||
|
if(start < first_pixel) start = first_pixel;
|
||||||
|
if(start >= end) return;
|
||||||
|
|
||||||
|
// perform the visible part of the line, if any
|
||||||
|
if(start < 224)
|
||||||
|
{
|
||||||
|
draw_ball_visible(start - first_pixel_cycle + 4, std::min(end - first_pixel_cycle + 4, 160));
|
||||||
|
}
|
||||||
|
|
||||||
|
// move further if required
|
||||||
|
if(is_moving_[(int)MotionIndex::Ball] && end >= 224 && motion_time_[(int)MotionIndex::Ball] < end)
|
||||||
|
{
|
||||||
|
perform_motion_step((int)MotionIndex::Ball);
|
||||||
|
ball_.pixel_position = std::max(0, ball_.pixel_position - 1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void TIA::draw_ball_visible(int start, int end)
|
void TIA::draw_ball_visible(int start, int end)
|
||||||
{
|
{
|
||||||
|
int &position = position_[(int)MotionIndex::Ball];
|
||||||
|
|
||||||
|
// perform a miniature event loop on (i) triggering draws; (ii) drawing; and (iii) motion
|
||||||
|
int next_motion_time = motion_time_[(int)MotionIndex::Ball] - first_pixel_cycle + 4;
|
||||||
|
while(start < end)
|
||||||
|
{
|
||||||
|
int next_event_time = end;
|
||||||
|
|
||||||
|
// is the next event a movement tick?
|
||||||
|
if(is_moving_[(int)MotionIndex::Ball] && next_motion_time < next_event_time)
|
||||||
|
{
|
||||||
|
next_event_time = next_motion_time;
|
||||||
|
}
|
||||||
|
|
||||||
|
// is the next event a graphics trigger?
|
||||||
|
if(ball_.enabled[ball_.enabled_index])
|
||||||
|
{
|
||||||
|
int time_until_copy = 160 - position;
|
||||||
|
int next_copy_time = start + time_until_copy;
|
||||||
|
if(next_copy_time < next_event_time) next_event_time = next_copy_time;
|
||||||
|
}
|
||||||
|
|
||||||
|
// the decision is to progress by length
|
||||||
|
const int length = next_event_time - start;
|
||||||
|
|
||||||
|
if(ball_.pixel_position)
|
||||||
|
{
|
||||||
|
int output_cursor = 0;
|
||||||
|
if(ball_.enabled[ball_.enabled_index])
|
||||||
|
{
|
||||||
|
while(ball_.pixel_position && output_cursor < length)
|
||||||
|
{
|
||||||
|
collision_buffer_[start + output_cursor] |= (uint8_t)CollisionType::Ball;
|
||||||
|
output_cursor++;
|
||||||
|
ball_.pixel_position--;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ball_.pixel_position = std::max(0, ball_.pixel_position - length);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// the next interesting event is after next_event_time cycles, so progress
|
||||||
|
position = (position + length) % 160;
|
||||||
|
start = next_event_time;
|
||||||
|
|
||||||
|
// if the event is a motion tick, apply
|
||||||
|
if(is_moving_[(int)MotionIndex::Ball] && start == next_motion_time)
|
||||||
|
{
|
||||||
|
perform_motion_step((int)MotionIndex::Ball);
|
||||||
|
next_motion_time += 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
// if it's a draw trigger, trigger a draw
|
||||||
|
if(!position)
|
||||||
|
{
|
||||||
|
ball_.pixel_position = ball_.size;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -153,6 +153,17 @@ class TIA {
|
|||||||
int size; // 0 = 1 pixel, 1 = 2 pixels, etc
|
int size; // 0 = 1 pixel, 1 = 2 pixels, etc
|
||||||
} missile_[2];
|
} missile_[2];
|
||||||
|
|
||||||
|
// ball state
|
||||||
|
struct Ball {
|
||||||
|
bool enabled[2];
|
||||||
|
int enabled_index;
|
||||||
|
int size;
|
||||||
|
|
||||||
|
int pixel_position;
|
||||||
|
|
||||||
|
Ball() : pixel_position(0), size(1), enabled_index(0) {}
|
||||||
|
} ball_;
|
||||||
|
|
||||||
// movement
|
// movement
|
||||||
bool horizontal_blank_extend_;
|
bool horizontal_blank_extend_;
|
||||||
int motion_[5];
|
int motion_[5];
|
||||||
|
Loading…
x
Reference in New Issue
Block a user