mirror of
https://github.com/TomHarte/CLK.git
synced 2024-08-19 21:29:04 +00:00
Switched video to postfix underscores, for consistency.
This commit is contained in:
parent
707763f80b
commit
5ebc1c63ff
@ -20,18 +20,17 @@ namespace {
|
|||||||
}
|
}
|
||||||
|
|
||||||
VideoOutput::VideoOutput(uint8_t *memory) :
|
VideoOutput::VideoOutput(uint8_t *memory) :
|
||||||
_ram(memory),
|
ram_(memory),
|
||||||
_frame_counter(0), _counter(0),
|
frame_counter_(0), counter_(0),
|
||||||
_is_graphics_mode(false),
|
is_graphics_mode_(false),
|
||||||
_character_set_base_address(0xb400),
|
character_set_base_address_(0xb400),
|
||||||
_phase(0),
|
phase_(0),
|
||||||
_v_sync_start_position(PAL50VSyncStartPosition), _v_sync_end_position(PAL50VSyncEndPosition),
|
v_sync_start_position_(PAL50VSyncStartPosition), v_sync_end_position_(PAL50VSyncEndPosition),
|
||||||
_counter_period(PAL50Period), _next_frame_is_sixty_hertz(false)
|
counter_period_(PAL50Period), next_frame_is_sixty_hertz_(false),
|
||||||
|
crt_(new Outputs::CRT::CRT(64*6, 6, Outputs::CRT::DisplayType::PAL50, 1))
|
||||||
{
|
{
|
||||||
_crt.reset(new Outputs::CRT::CRT(64*6, 6, Outputs::CRT::DisplayType::PAL50, 1));
|
|
||||||
|
|
||||||
// TODO: this is a copy and paste from the Electron; factor out.
|
// TODO: this is a copy and paste from the Electron; factor out.
|
||||||
_crt->set_rgb_sampling_function(
|
crt_->set_rgb_sampling_function(
|
||||||
"vec3 rgb_sample(usampler2D sampler, vec2 coordinate, vec2 icoordinate)"
|
"vec3 rgb_sample(usampler2D sampler, vec2 coordinate, vec2 icoordinate)"
|
||||||
"{"
|
"{"
|
||||||
"uint texValue = texture(sampler, coordinate).r;"
|
"uint texValue = texture(sampler, coordinate).r;"
|
||||||
@ -39,13 +38,13 @@ VideoOutput::VideoOutput(uint8_t *memory) :
|
|||||||
"return vec3( uvec3(texValue) & uvec3(4u, 2u, 1u));"
|
"return vec3( uvec3(texValue) & uvec3(4u, 2u, 1u));"
|
||||||
"}");
|
"}");
|
||||||
|
|
||||||
_crt->set_output_device(Outputs::CRT::Television);
|
crt_->set_output_device(Outputs::CRT::Television);
|
||||||
_crt->set_visible_area(_crt->get_rect_for_area(50, 224, 16 * 6, 40 * 6, 4.0f / 3.0f));
|
crt_->set_visible_area(crt_->get_rect_for_area(50, 224, 16 * 6, 40 * 6, 4.0f / 3.0f));
|
||||||
}
|
}
|
||||||
|
|
||||||
std::shared_ptr<Outputs::CRT::CRT> VideoOutput::get_crt()
|
std::shared_ptr<Outputs::CRT::CRT> VideoOutput::get_crt()
|
||||||
{
|
{
|
||||||
return _crt;
|
return crt_;
|
||||||
}
|
}
|
||||||
|
|
||||||
void VideoOutput::run_for_cycles(int number_of_cycles)
|
void VideoOutput::run_for_cycles(int number_of_cycles)
|
||||||
@ -58,58 +57,58 @@ void VideoOutput::run_for_cycles(int number_of_cycles)
|
|||||||
|
|
||||||
while(number_of_cycles)
|
while(number_of_cycles)
|
||||||
{
|
{
|
||||||
int h_counter =_counter & 63;
|
int h_counter = counter_ & 63;
|
||||||
int cycles_run_for = 0;
|
int cycles_run_for = 0;
|
||||||
|
|
||||||
if(_counter >= _v_sync_start_position && _counter < _v_sync_end_position)
|
if(counter_ >= v_sync_start_position_ && counter_ < v_sync_end_position_)
|
||||||
{
|
{
|
||||||
// this is a sync line
|
// this is a sync line
|
||||||
cycles_run_for = _v_sync_end_position - _counter;
|
cycles_run_for = v_sync_end_position_ - counter_;
|
||||||
clamp(_crt->output_sync((unsigned int)(_v_sync_end_position - _v_sync_start_position) * 6));
|
clamp(crt_->output_sync((unsigned int)(v_sync_end_position_ - v_sync_start_position_) * 6));
|
||||||
}
|
}
|
||||||
else if(_counter < 224*64 && h_counter < 40)
|
else if(counter_ < 224*64 && h_counter < 40)
|
||||||
{
|
{
|
||||||
// this is a pixel line
|
// this is a pixel line
|
||||||
if(!h_counter)
|
if(!h_counter)
|
||||||
{
|
{
|
||||||
_ink = 0xff;
|
ink_ = 0xff;
|
||||||
_paper = 0x00;
|
paper_ = 0x00;
|
||||||
_use_alternative_character_set = _use_double_height_characters = _blink_text = false;
|
use_alternative_character_set_ = use_double_height_characters_ = blink_text_ = false;
|
||||||
set_character_set_base_address();
|
set_character_set_base_address();
|
||||||
_phase += 64;
|
phase_ += 64;
|
||||||
_pixel_target = _crt->allocate_write_area(120);
|
pixel_target_ = crt_->allocate_write_area(120);
|
||||||
|
|
||||||
if(!_counter)
|
if(!counter_)
|
||||||
{
|
{
|
||||||
_phase += 128; // TODO: incorporate all the lines that were missed
|
phase_ += 128; // TODO: incorporate all the lines that were missed
|
||||||
_frame_counter++;
|
frame_counter_++;
|
||||||
|
|
||||||
_v_sync_start_position = _next_frame_is_sixty_hertz ? PAL60VSyncStartPosition : PAL50VSyncStartPosition;
|
v_sync_start_position_ = next_frame_is_sixty_hertz_ ? PAL60VSyncStartPosition : PAL50VSyncStartPosition;
|
||||||
_v_sync_end_position = _next_frame_is_sixty_hertz ? PAL60VSyncEndPosition : PAL50VSyncEndPosition;
|
v_sync_end_position_ = next_frame_is_sixty_hertz_ ? PAL60VSyncEndPosition : PAL50VSyncEndPosition;
|
||||||
_counter_period = _next_frame_is_sixty_hertz ? PAL60Period : PAL50Period;
|
counter_period_ = next_frame_is_sixty_hertz_ ? PAL60Period : PAL50Period;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
cycles_run_for = std::min(40 - h_counter, number_of_cycles);
|
cycles_run_for = std::min(40 - h_counter, number_of_cycles);
|
||||||
int columns = cycles_run_for;
|
int columns = cycles_run_for;
|
||||||
int pixel_base_address = 0xa000 + (_counter >> 6) * 40;
|
int pixel_base_address = 0xa000 + (counter_ >> 6) * 40;
|
||||||
int character_base_address = 0xbb80 + (_counter >> 9) * 40;
|
int character_base_address = 0xbb80 + (counter_ >> 9) * 40;
|
||||||
uint8_t blink_mask = (_blink_text && (_frame_counter&32)) ? 0x00 : 0xff;
|
uint8_t blink_mask = (blink_text_ && (frame_counter_&32)) ? 0x00 : 0xff;
|
||||||
|
|
||||||
while(columns--)
|
while(columns--)
|
||||||
{
|
{
|
||||||
uint8_t pixels, control_byte;
|
uint8_t pixels, control_byte;
|
||||||
|
|
||||||
if(_is_graphics_mode && _counter < 200*64)
|
if(is_graphics_mode_ && counter_ < 200*64)
|
||||||
{
|
{
|
||||||
control_byte = pixels = _ram[pixel_base_address + h_counter];
|
control_byte = pixels = ram_[pixel_base_address + h_counter];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
int address = character_base_address + h_counter;
|
int address = character_base_address + h_counter;
|
||||||
control_byte = _ram[address];
|
control_byte = ram_[address];
|
||||||
int line = _use_double_height_characters ? ((_counter >> 7) & 7) : ((_counter >> 6) & 7);
|
int line = use_double_height_characters_ ? ((counter_ >> 7) & 7) : ((counter_ >> 6) & 7);
|
||||||
pixels = _ram[_character_set_base_address + (control_byte&127) * 8 + line];
|
pixels = ram_[character_set_base_address_ + (control_byte&127) * 8 + line];
|
||||||
}
|
}
|
||||||
|
|
||||||
uint8_t inverse_mask = (control_byte & 0x80) ? 0x77 : 0x00;
|
uint8_t inverse_mask = (control_byte & 0x80) ? 0x77 : 0x00;
|
||||||
@ -117,65 +116,65 @@ void VideoOutput::run_for_cycles(int number_of_cycles)
|
|||||||
|
|
||||||
if(control_byte & 0x60)
|
if(control_byte & 0x60)
|
||||||
{
|
{
|
||||||
if(_pixel_target)
|
if(pixel_target_)
|
||||||
{
|
{
|
||||||
uint8_t colours[2] = {
|
uint8_t colours[2] = {
|
||||||
(uint8_t)(_paper ^ inverse_mask),
|
(uint8_t)(paper_ ^ inverse_mask),
|
||||||
(uint8_t)(_ink ^ inverse_mask),
|
(uint8_t)(ink_ ^ inverse_mask),
|
||||||
};
|
};
|
||||||
|
|
||||||
_pixel_target[0] = (colours[(pixels >> 4)&1] & 0x0f) | (colours[(pixels >> 5)&1] & 0xf0);
|
pixel_target_[0] = (colours[(pixels >> 4)&1] & 0x0f) | (colours[(pixels >> 5)&1] & 0xf0);
|
||||||
_pixel_target[1] = (colours[(pixels >> 2)&1] & 0x0f) | (colours[(pixels >> 3)&1] & 0xf0);
|
pixel_target_[1] = (colours[(pixels >> 2)&1] & 0x0f) | (colours[(pixels >> 3)&1] & 0xf0);
|
||||||
_pixel_target[2] = (colours[(pixels >> 0)&1] & 0x0f) | (colours[(pixels >> 1)&1] & 0xf0);
|
pixel_target_[2] = (colours[(pixels >> 0)&1] & 0x0f) | (colours[(pixels >> 1)&1] & 0xf0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
switch(control_byte & 0x1f)
|
switch(control_byte & 0x1f)
|
||||||
{
|
{
|
||||||
case 0x00: _ink = 0x00; break;
|
case 0x00: ink_ = 0x00; break;
|
||||||
case 0x01: _ink = 0x44; break;
|
case 0x01: ink_ = 0x44; break;
|
||||||
case 0x02: _ink = 0x22; break;
|
case 0x02: ink_ = 0x22; break;
|
||||||
case 0x03: _ink = 0x66; break;
|
case 0x03: ink_ = 0x66; break;
|
||||||
case 0x04: _ink = 0x11; break;
|
case 0x04: ink_ = 0x11; break;
|
||||||
case 0x05: _ink = 0x55; break;
|
case 0x05: ink_ = 0x55; break;
|
||||||
case 0x06: _ink = 0x33; break;
|
case 0x06: ink_ = 0x33; break;
|
||||||
case 0x07: _ink = 0x77; break;
|
case 0x07: ink_ = 0x77; break;
|
||||||
|
|
||||||
case 0x08: case 0x09: case 0x0a: case 0x0b:
|
case 0x08: case 0x09: case 0x0a: case 0x0b:
|
||||||
case 0x0c: case 0x0d: case 0x0e: case 0x0f:
|
case 0x0c: case 0x0d: case 0x0e: case 0x0f:
|
||||||
_use_alternative_character_set = (control_byte&1);
|
use_alternative_character_set_ = (control_byte&1);
|
||||||
_use_double_height_characters = (control_byte&2);
|
use_double_height_characters_ = (control_byte&2);
|
||||||
_blink_text = (control_byte&4);
|
blink_text_ = (control_byte&4);
|
||||||
set_character_set_base_address();
|
set_character_set_base_address();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0x10: _paper = 0x00; break;
|
case 0x10: paper_ = 0x00; break;
|
||||||
case 0x11: _paper = 0x44; break;
|
case 0x11: paper_ = 0x44; break;
|
||||||
case 0x12: _paper = 0x22; break;
|
case 0x12: paper_ = 0x22; break;
|
||||||
case 0x13: _paper = 0x66; break;
|
case 0x13: paper_ = 0x66; break;
|
||||||
case 0x14: _paper = 0x11; break;
|
case 0x14: paper_ = 0x11; break;
|
||||||
case 0x15: _paper = 0x55; break;
|
case 0x15: paper_ = 0x55; break;
|
||||||
case 0x16: _paper = 0x33; break;
|
case 0x16: paper_ = 0x33; break;
|
||||||
case 0x17: _paper = 0x77; break;
|
case 0x17: paper_ = 0x77; break;
|
||||||
|
|
||||||
case 0x18: case 0x19: case 0x1a: case 0x1b:
|
case 0x18: case 0x19: case 0x1a: case 0x1b:
|
||||||
case 0x1c: case 0x1d: case 0x1e: case 0x1f:
|
case 0x1c: case 0x1d: case 0x1e: case 0x1f:
|
||||||
_is_graphics_mode = (control_byte & 4);
|
is_graphics_mode_ = (control_byte & 4);
|
||||||
_next_frame_is_sixty_hertz = !(control_byte & 2);
|
next_frame_is_sixty_hertz_ = !(control_byte & 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default: break;
|
default: break;
|
||||||
}
|
}
|
||||||
if(_pixel_target) _pixel_target[0] = _pixel_target[1] = _pixel_target[2] = (uint8_t)(_paper ^ inverse_mask);
|
if(pixel_target_) pixel_target_[0] = pixel_target_[1] = pixel_target_[2] = (uint8_t)(paper_ ^ inverse_mask);
|
||||||
}
|
}
|
||||||
if(_pixel_target) _pixel_target += 3;
|
if(pixel_target_) pixel_target_ += 3;
|
||||||
h_counter++;
|
h_counter++;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(h_counter == 40)
|
if(h_counter == 40)
|
||||||
{
|
{
|
||||||
_crt->output_data(40 * 6, 2);
|
crt_->output_data(40 * 6, 2);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -185,34 +184,34 @@ void VideoOutput::run_for_cycles(int number_of_cycles)
|
|||||||
{
|
{
|
||||||
cycles_run_for = 48 - h_counter;
|
cycles_run_for = 48 - h_counter;
|
||||||
clamp(
|
clamp(
|
||||||
int period = (_counter < 224*64) ? 8 : 48;
|
int period = (counter_ < 224*64) ? 8 : 48;
|
||||||
_crt->output_blank((unsigned int)period * 6);
|
crt_->output_blank((unsigned int)period * 6);
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else if(h_counter < 54)
|
else if(h_counter < 54)
|
||||||
{
|
{
|
||||||
cycles_run_for = 54 - h_counter;
|
cycles_run_for = 54 - h_counter;
|
||||||
clamp(_crt->output_sync(6 * 6));
|
clamp(crt_->output_sync(6 * 6));
|
||||||
}
|
}
|
||||||
else if(h_counter < 56)
|
else if(h_counter < 56)
|
||||||
{
|
{
|
||||||
cycles_run_for = 56 - h_counter;
|
cycles_run_for = 56 - h_counter;
|
||||||
clamp(_crt->output_colour_burst(2 * 6, _phase, 128));
|
clamp(crt_->output_colour_burst(2 * 6, phase_, 128));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
cycles_run_for = 64 - h_counter;
|
cycles_run_for = 64 - h_counter;
|
||||||
clamp(_crt->output_blank(8 * 6));
|
clamp(crt_->output_blank(8 * 6));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_counter = (_counter + cycles_run_for)%_counter_period;
|
counter_ = (counter_ + cycles_run_for)%counter_period_;
|
||||||
number_of_cycles -= cycles_run_for;
|
number_of_cycles -= cycles_run_for;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void VideoOutput::set_character_set_base_address()
|
void VideoOutput::set_character_set_base_address()
|
||||||
{
|
{
|
||||||
if(_is_graphics_mode) _character_set_base_address = _use_alternative_character_set ? 0x9c00 : 0x9800;
|
if(is_graphics_mode_) character_set_base_address_ = use_alternative_character_set_ ? 0x9c00 : 0x9800;
|
||||||
else _character_set_base_address = _use_alternative_character_set ? 0xb800 : 0xb400;
|
else character_set_base_address_ = use_alternative_character_set_ ? 0xb800 : 0xb400;
|
||||||
}
|
}
|
||||||
|
@ -20,29 +20,29 @@ class VideoOutput {
|
|||||||
void run_for_cycles(int number_of_cycles);
|
void run_for_cycles(int number_of_cycles);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
uint8_t *_ram;
|
uint8_t *ram_;
|
||||||
std::shared_ptr<Outputs::CRT::CRT> _crt;
|
std::shared_ptr<Outputs::CRT::CRT> crt_;
|
||||||
|
|
||||||
// Counters and limits
|
// Counters and limits
|
||||||
int _counter, _frame_counter;
|
int counter_, frame_counter_;
|
||||||
int _v_sync_start_position, _v_sync_end_position, _counter_period;
|
int v_sync_start_position_, v_sync_end_position_, counter_period_;
|
||||||
|
|
||||||
// Output target
|
// Output target
|
||||||
uint8_t *_pixel_target;
|
uint8_t *pixel_target_;
|
||||||
|
|
||||||
// Registers
|
// Registers
|
||||||
uint8_t _ink, _paper;
|
uint8_t ink_, paper_;
|
||||||
|
|
||||||
int _character_set_base_address;
|
int character_set_base_address_;
|
||||||
inline void set_character_set_base_address();
|
inline void set_character_set_base_address();
|
||||||
|
|
||||||
bool _is_graphics_mode;
|
bool is_graphics_mode_;
|
||||||
bool _next_frame_is_sixty_hertz;
|
bool next_frame_is_sixty_hertz_;
|
||||||
bool _use_alternative_character_set;
|
bool use_alternative_character_set_;
|
||||||
bool _use_double_height_characters;
|
bool use_double_height_characters_;
|
||||||
bool _blink_text;
|
bool blink_text_;
|
||||||
|
|
||||||
uint8_t _phase;
|
uint8_t phase_;
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user