1
0
mirror of https://github.com/TomHarte/CLK.git synced 2024-07-11 04:28:58 +00:00

Quickest first attempt to switch to instancing for the output array. Texture coordinates seem to be off.

This commit is contained in:
Thomas Harte 2016-05-10 07:23:47 -04:00
parent 4592458ea0
commit 86dab3a5d6
5 changed files with 44 additions and 21 deletions

View File

@ -96,10 +96,12 @@ Flywheel::SyncEvent CRT::get_next_horizontal_sync_event(bool hsync_is_requested,
return _horizontal_flywheel->get_next_event_in_period(hsync_is_requested, cycles_to_run_for, cycles_advanced); return _horizontal_flywheel->get_next_event_in_period(hsync_is_requested, cycles_to_run_for, cycles_advanced);
} }
#define output_position_x(v) (*(uint16_t *)&next_run[OutputVertexSize*v + OutputVertexOffsetOfPosition + 0]) #define output_position_x1() (*(uint16_t *)&next_run[OutputVertexOffsetOfPosition + 0])
#define output_position_y(v) (*(uint16_t *)&next_run[OutputVertexSize*v + OutputVertexOffsetOfPosition + 2]) #define output_position_x2() (*(uint16_t *)&next_run[OutputVertexOffsetOfTerminators + 0])
#define output_tex_x(v) (*(uint16_t *)&next_run[OutputVertexSize*v + OutputVertexOffsetOfTexCoord + 0]) #define output_position_y() (*(uint16_t *)&next_run[OutputVertexOffsetOfPosition + 2])
#define output_tex_y(v) (*(uint16_t *)&next_run[OutputVertexSize*v + OutputVertexOffsetOfTexCoord + 2]) #define output_tex_x1() (*(uint16_t *)&next_run[OutputVertexOffsetOfTexCoord + 0])
#define output_tex_x2() (*(uint16_t *)&next_run[OutputVertexOffsetOfTerminators + 2])
#define output_tex_y() (*(uint16_t *)&next_run[OutputVertexOffsetOfTexCoord + 2])
#define source_input_position_x(v) (*(uint16_t *)&next_run[SourceVertexSize*v + SourceVertexOffsetOfInputPosition + 0]) #define source_input_position_x(v) (*(uint16_t *)&next_run[SourceVertexSize*v + SourceVertexOffsetOfInputPosition + 0])
#define source_input_position_y(v) (*(uint16_t *)&next_run[SourceVertexSize*v + SourceVertexOffsetOfInputPosition + 2]) #define source_input_position_y(v) (*(uint16_t *)&next_run[SourceVertexSize*v + SourceVertexOffsetOfInputPosition + 2])
@ -188,18 +190,26 @@ void CRT::advance_cycles(unsigned int number_of_cycles, unsigned int source_divi
{ {
if( if(
_is_writing_composite_run == _did_start_run && _is_writing_composite_run == _did_start_run &&
_openGL_output_builder->composite_output_run_has_room_for_vertices(_did_start_run ? 3 : 6) && _openGL_output_builder->composite_output_run_has_room_for_vertex() &&
!_openGL_output_builder->composite_output_buffer_is_full()) !_openGL_output_builder->composite_output_buffer_is_full())
{ {
uint8_t *next_run = _openGL_output_builder->get_next_output_run(); uint8_t *next_run = _openGL_output_builder->get_next_output_run();
if(next_run) if(next_run)
{ {
output_position_x(0) = output_position_x(1) = output_position_x(2) = (uint16_t)_horizontal_flywheel->get_current_output_position(); if(_did_start_run)
output_position_y(0) = output_position_y(1) = output_position_y(2) = (uint16_t)(_vertical_flywheel->get_current_output_position() / _vertical_flywheel_output_divider); {
output_tex_x(0) = output_tex_x(1) = output_tex_x(2) = (uint16_t)_horizontal_flywheel->get_current_output_position(); output_position_x1() = (uint16_t)_horizontal_flywheel->get_current_output_position();
output_tex_y(0) = output_tex_y(1) = output_tex_y(2) = _openGL_output_builder->get_composite_output_y(); output_position_y() = (uint16_t)(_vertical_flywheel->get_current_output_position() / _vertical_flywheel_output_divider);
output_tex_x1() = (uint16_t)_horizontal_flywheel->get_current_output_position();
output_tex_y() = _openGL_output_builder->get_composite_output_y();
}
else
{
output_position_x2() = (uint16_t)_horizontal_flywheel->get_current_output_position();
output_tex_x2() = (uint16_t)_horizontal_flywheel->get_current_output_position();
_openGL_output_builder->complete_output_run();
}
_openGL_output_builder->complete_output_run(3);
_did_start_run ^= true; _did_start_run ^= true;
} }
} }

View File

@ -19,8 +19,9 @@ namespace CRT {
// or is one of the intermediate buffers that we've used to convert from composite towards RGB. // or is one of the intermediate buffers that we've used to convert from composite towards RGB.
const GLsizei OutputVertexOffsetOfPosition = 0; const GLsizei OutputVertexOffsetOfPosition = 0;
const GLsizei OutputVertexOffsetOfTexCoord = 4; const GLsizei OutputVertexOffsetOfTexCoord = 4;
const GLsizei OutputVertexOffsetOfTerminators = 6;
const GLsizei OutputVertexSize = 8; const GLsizei OutputVertexSize = 12;
// Input vertices, used only in composite mode, map from the input buffer to temporary buffer locations; such // Input vertices, used only in composite mode, map from the input buffer to temporary buffer locations; such
// remapping occurs to ensure a continous stream of data for each scan, giving correct out-of-bounds behaviour // remapping occurs to ensure a continous stream of data for each scan, giving correct out-of-bounds behaviour

View File

@ -324,7 +324,8 @@ void OpenGLOutputBuilder::draw_frame(unsigned int output_width, unsigned int out
output_shader_program->bind(); output_shader_program->bind();
// draw // draw
glDrawArrays(GL_TRIANGLE_STRIP, 0, submitted_output_data / OutputVertexSize); // glDrawArrays(GL_TRIANGLE_STRIP, 0, submitted_output_data / OutputVertexSize);
glDrawArraysInstanced(GL_TRIANGLE_STRIP, 0, 4, submitted_output_data / OutputVertexSize);
} }
// copy framebuffer to the intended place // copy framebuffer to the intended place
@ -425,16 +426,23 @@ void OpenGLOutputBuilder::prepare_output_vertex_array()
{ {
GLint positionAttribute = output_shader_program->get_attrib_location("position"); GLint positionAttribute = output_shader_program->get_attrib_location("position");
GLint textureCoordinatesAttribute = output_shader_program->get_attrib_location("srcCoordinates"); GLint textureCoordinatesAttribute = output_shader_program->get_attrib_location("srcCoordinates");
GLint terminatorsAttribute = output_shader_program->get_attrib_location("terminators");
glBindVertexArray(output_vertex_array); glBindVertexArray(output_vertex_array);
glEnableVertexAttribArray((GLuint)positionAttribute); glEnableVertexAttribArray((GLuint)positionAttribute);
glEnableVertexAttribArray((GLuint)textureCoordinatesAttribute); glEnableVertexAttribArray((GLuint)textureCoordinatesAttribute);
glEnableVertexAttribArray((GLuint)terminatorsAttribute);
const GLsizei vertexStride = OutputVertexSize; const GLsizei vertexStride = OutputVertexSize;
glBindBuffer(GL_ARRAY_BUFFER, output_array_buffer); glBindBuffer(GL_ARRAY_BUFFER, output_array_buffer);
glVertexAttribPointer((GLuint)positionAttribute, 2, GL_UNSIGNED_SHORT, GL_FALSE, vertexStride, (void *)OutputVertexOffsetOfPosition); glVertexAttribPointer((GLuint)positionAttribute, 2, GL_UNSIGNED_SHORT, GL_FALSE, vertexStride, (void *)OutputVertexOffsetOfPosition);
glVertexAttribPointer((GLuint)textureCoordinatesAttribute, 2, GL_UNSIGNED_SHORT, GL_FALSE, vertexStride, (void *)OutputVertexOffsetOfTexCoord); glVertexAttribPointer((GLuint)textureCoordinatesAttribute, 2, GL_UNSIGNED_SHORT, GL_FALSE, vertexStride, (void *)OutputVertexOffsetOfTexCoord);
glVertexAttribPointer((GLuint)terminatorsAttribute, 2, GL_UNSIGNED_SHORT, GL_FALSE, vertexStride, (void *)OutputVertexOffsetOfTerminators);
glVertexAttribDivisor((GLuint)positionAttribute, 1);
glVertexAttribDivisor((GLuint)textureCoordinatesAttribute, 1);
glVertexAttribDivisor((GLuint)terminatorsAttribute, 1);
} }
} }

View File

@ -115,9 +115,9 @@ class OpenGLOutputBuilder {
_source_buffer_data_pointer += 2 * SourceVertexSize; _source_buffer_data_pointer += 2 * SourceVertexSize;
} }
inline bool composite_output_run_has_room_for_vertices(GLsizei vertices_to_write) inline bool composite_output_run_has_room_for_vertex()
{ {
return _output_buffer_data_pointer <= OutputVertexBufferDataSize - vertices_to_write * OutputVertexSize; return _output_buffer_data_pointer < OutputVertexBufferDataSize;
} }
inline uint8_t *get_next_output_run() inline uint8_t *get_next_output_run()
@ -126,9 +126,9 @@ class OpenGLOutputBuilder {
return &_output_buffer_data.get()[_output_buffer_data_pointer % OutputVertexBufferDataSize]; return &_output_buffer_data.get()[_output_buffer_data_pointer % OutputVertexBufferDataSize];
} }
inline void complete_output_run(GLsizei vertices_written) inline void complete_output_run()
{ {
_output_buffer_data_pointer += vertices_written * OutputVertexSize; _output_buffer_data_pointer += OutputVertexSize;
} }
inline void lock_output() inline void lock_output()

View File

@ -32,6 +32,7 @@ std::unique_ptr<OutputShader> OutputShader::make_shader(const char *fragment_met
"in vec2 position;" "in vec2 position;"
"in vec2 srcCoordinates;" "in vec2 srcCoordinates;"
"in vec2 terminators;"
"uniform vec2 boundsOrigin;" "uniform vec2 boundsOrigin;"
"uniform vec2 boundsSize;" "uniform vec2 boundsSize;"
@ -45,15 +46,18 @@ std::unique_ptr<OutputShader> OutputShader::make_shader(const char *fragment_met
"void main(void)" "void main(void)"
"{" "{"
"float laterals[] = float[](0, 0, 1, 0, 1, 1);" "float lateral = float(gl_VertexID & 1);"
"float lateral = laterals[gl_VertexID %% 6];" "float longitudinal = float((gl_VertexID & 2) >> 1);"
"lateralVarying = lateral - 0.5;" "lateralVarying = lateral - 0.5;"
"vec2 vSrcCoordinates = mix(srcCoordinates, vec2(terminators.y, srcCoordinates.y), longitudinal);"
"ivec2 textureSize = textureSize(texID, 0);" "ivec2 textureSize = textureSize(texID, 0);"
"iSrcCoordinatesVarying = srcCoordinates;" "iSrcCoordinatesVarying = vSrcCoordinates;"
"srcCoordinatesVarying = vec2(srcCoordinates.x / textureSize.x, (srcCoordinates.y + 0.5) / textureSize.y);" "srcCoordinatesVarying = vec2(vSrcCoordinates.x / textureSize.x, (vSrcCoordinates.y + 0.5) / textureSize.y);"
"vec2 floatingPosition = (position / positionConversion) + lateral * scanNormal;" "vec2 vPosition = mix(position, vec2(terminators.x, position.y), longitudinal);"
"vec2 floatingPosition = (vPosition / positionConversion) + lateral * scanNormal;"
"vec2 mappedPosition = (floatingPosition - boundsOrigin) / boundsSize;" "vec2 mappedPosition = (floatingPosition - boundsOrigin) / boundsSize;"
"gl_Position = vec4(mappedPosition.x * 2.0 - 1.0, 1.0 - mappedPosition.y * 2.0, 0.0, 1.0);" "gl_Position = vec4(mappedPosition.x * 2.0 - 1.0, 1.0 - mappedPosition.y * 2.0, 0.0, 1.0);"
"}", sampler_type); "}", sampler_type);