mirror of
https://github.com/GayPizzaSpecifications/padlab.git
synced 2025-08-03 05:10:56 +00:00
crude legacy GL backend w/ anti aliasing
This commit is contained in:
parent
fc9a6571ec
commit
9ba7a3bda8
@ -2,15 +2,26 @@ cmake_minimum_required(VERSION 3.1 FATAL_ERROR)
|
||||
project(padlab C)
|
||||
set(CMAKE_C_STANDARD 99)
|
||||
set(TARGET padlab)
|
||||
|
||||
find_package(SDL2 REQUIRED)
|
||||
find_package(OpenGL)
|
||||
|
||||
set(SOURCES
|
||||
maths.h
|
||||
draw.c draw.h
|
||||
draw.h
|
||||
stick.c stick.h
|
||||
analogue.c)
|
||||
|
||||
find_package(SDL2 REQUIRED)
|
||||
if (OPENGL_FOUND)
|
||||
list(APPEND SOURCES draw_opengl.c)
|
||||
else()
|
||||
list(APPEND SOURCES draw.c)
|
||||
endif()
|
||||
|
||||
add_executable(${TARGET} ${SOURCES})
|
||||
target_link_libraries(${TARGET} SDL2::SDL2 m)
|
||||
if (OPENGL_FOUND)
|
||||
target_link_libraries(${TARGET} OpenGL::GL)
|
||||
endif()
|
||||
target_compile_options(${TARGET} PRIVATE
|
||||
-Wall -Wextra -pedantic -Wno-unused-parameter)
|
||||
|
@ -38,6 +38,7 @@ int main(int argc, char** argv)
|
||||
const int winflg = SDL_WINDOW_RESIZABLE | SDL_WINDOW_ALLOW_HIGHDPI;
|
||||
int winw = WINDOW_WIDTH;
|
||||
int winh = WINDOW_HEIGHT;
|
||||
DrawWindowHints();
|
||||
window = SDL_CreateWindow(CAPTION, winpos, winpos, winw, winh, winflg);
|
||||
FATAL(window == NULL, -1)
|
||||
|
||||
|
4
draw.c
4
draw.c
@ -4,6 +4,8 @@
|
||||
|
||||
static SDL_Renderer* rend = NULL;
|
||||
|
||||
void DrawWindowHints(void) {}
|
||||
|
||||
int InitDraw(SDL_Window* window)
|
||||
{
|
||||
const int rendflags = SDL_RENDERER_PRESENTVSYNC;
|
||||
@ -68,7 +70,7 @@ void DrawCircleSteps(int x, int y, int r, int steps)
|
||||
double stepsz = (double)TAU / steps;
|
||||
int lastx = r;
|
||||
int lasty = 0;
|
||||
for (int i = 0; i <= steps; ++i)
|
||||
for (int i = 1; i <= steps; ++i)
|
||||
{
|
||||
const double mag = (double)r;
|
||||
int ofsx = (int)round(cos(stepsz * i) * mag);
|
||||
|
4
draw.h
4
draw.h
@ -8,6 +8,10 @@
|
||||
|
||||
typedef struct SDL_Window SDL_Window;
|
||||
|
||||
// Call before window creation to setup backend-specific
|
||||
// hints and attributes.
|
||||
void DrawWindowHints(void);
|
||||
|
||||
// Initialise the drawing subsystem.
|
||||
//
|
||||
// Params:
|
||||
|
176
draw_opengl.c
Normal file
176
draw_opengl.c
Normal file
@ -0,0 +1,176 @@
|
||||
#include "draw.h"
|
||||
#include <SDL_video.h>
|
||||
#include <SDL_opengl.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
static SDL_GLContext* ctx = NULL;
|
||||
static SDL_Window* window = NULL;
|
||||
static uint32_t colour = 0x00000000;
|
||||
static uint32_t clrColour = 0x00000000;
|
||||
static double scaleWidth = 0.0;
|
||||
static double scaleHeight = 0.0;
|
||||
static bool antialias = false;
|
||||
|
||||
void DrawWindowHints(void)
|
||||
{
|
||||
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1); // Enable MSAA
|
||||
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 8); // 8x MSAA
|
||||
|
||||
// Legacy OpenGL profile
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 1);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, 1);
|
||||
SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_COMPATIBILITY);
|
||||
}
|
||||
|
||||
int InitDraw(SDL_Window* w)
|
||||
{
|
||||
ctx = SDL_GL_CreateContext(w);
|
||||
window = w;
|
||||
if (ctx == NULL || window == NULL)
|
||||
return -1;
|
||||
|
||||
SDL_GL_SetSwapInterval(1); // Enable vsync
|
||||
|
||||
// Detect if MSAA is available & active
|
||||
int res;
|
||||
if (SDL_GL_GetAttribute(SDL_GL_MULTISAMPLEBUFFERS, &res) == 0 && res == 1)
|
||||
if (SDL_GL_GetAttribute(SDL_GL_MULTISAMPLESAMPLES, &res) == 0 && res > 0)
|
||||
antialias = true;
|
||||
|
||||
// Disable depth test & culling, enable MSAA
|
||||
glDisable(GL_DEPTH_TEST);
|
||||
glDisable(GL_CULL_FACE);
|
||||
glEnable(GL_MULTISAMPLE);
|
||||
|
||||
GetDrawSizeInPixels(); // Fills scaleWidth & scaleHeight
|
||||
|
||||
// Setup orthographic viewport
|
||||
glMatrixMode(GL_PROJECTION);
|
||||
glOrtho(0.0, 1.0f, 1.0f, 0.0, 1.0, -1.0);
|
||||
glMatrixMode(GL_MODELVIEW);
|
||||
glLoadIdentity();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void QuitDraw(void)
|
||||
{
|
||||
SDL_GL_DeleteContext(ctx);
|
||||
ctx = NULL;
|
||||
window = NULL;
|
||||
}
|
||||
|
||||
|
||||
size GetDrawSizeInPixels(void)
|
||||
{
|
||||
size out;
|
||||
SDL_GL_GetDrawableSize(SDL_GL_GetCurrentWindow(), &out.w, &out.h);
|
||||
scaleWidth = 1.0 / (double)out.w;
|
||||
scaleHeight = 1.0 / (double)out.h;
|
||||
return out;
|
||||
}
|
||||
|
||||
|
||||
void SetDrawColour(uint32_t c)
|
||||
{
|
||||
colour = c;
|
||||
}
|
||||
|
||||
void DrawClear(void)
|
||||
{
|
||||
if (clrColour != colour)
|
||||
{
|
||||
const float mul = 1.0f / 255.0f;
|
||||
glClearColor(
|
||||
(GLclampf)((colour & 0xFF000000) >> 24) * mul,
|
||||
(GLclampf)((colour & 0x00FF0000) >> 16) * mul,
|
||||
(GLclampf)((colour & 0x0000FF00) >> 8) * mul,
|
||||
(GLclampf)((colour & 0x000000FF)) * mul);
|
||||
clrColour = colour;
|
||||
}
|
||||
glClear(GL_COLOR_BUFFER_BIT);
|
||||
}
|
||||
|
||||
static inline void GlColour(void)
|
||||
{
|
||||
const float mul = 1.0f / 255.0f;
|
||||
glColor4f(
|
||||
(GLclampf)((colour & 0xFF000000) >> 24) * mul,
|
||||
(GLclampf)((colour & 0x00FF0000) >> 16) * mul,
|
||||
(GLclampf)((colour & 0x0000FF00) >> 8) * mul,
|
||||
(GLclampf)((colour & 0x000000FF)) * mul);
|
||||
}
|
||||
|
||||
void DrawPoint(int x, int y)
|
||||
{
|
||||
const double fx = ((double)x) * scaleWidth;
|
||||
const double fy = ((double)y) * scaleHeight;
|
||||
|
||||
glBegin(GL_POINTS);
|
||||
GlColour();
|
||||
glVertex2d(fx, fy);
|
||||
glEnd();
|
||||
}
|
||||
|
||||
void DrawRect(int x, int y, int w, int h)
|
||||
{
|
||||
const double fx = (double)x * scaleWidth;
|
||||
const double fy = (double)y * scaleHeight;
|
||||
const double fw = (double)w * scaleWidth;
|
||||
const double fh = (double)h * scaleHeight;
|
||||
|
||||
glBegin(GL_LINE_LOOP);
|
||||
GlColour();
|
||||
glVertex2d(fx, fy);
|
||||
glVertex2d(fx + fw, fy);
|
||||
glVertex2d(fx + fw, fy + fh);
|
||||
glVertex2d(fx, fy + fh);
|
||||
glEnd();
|
||||
}
|
||||
|
||||
void DrawLine(int x1, int y1, int x2, int y2)
|
||||
{
|
||||
const double fx1 = (double)x1 * scaleWidth;
|
||||
const double fy1 = (double)y1 * scaleHeight;
|
||||
const double fx2 = (double)x2 * scaleWidth;
|
||||
const double fy2 = (double)y2 * scaleHeight;
|
||||
|
||||
glBegin(GL_LINES);
|
||||
GlColour();
|
||||
glVertex2d(fx1, fy1);
|
||||
glVertex2d(fx2, fy2);
|
||||
glEnd();
|
||||
}
|
||||
|
||||
void DrawCircle(int x, int y, int r)
|
||||
{
|
||||
DrawCircleSteps(x, y, r, (int)(sqrt((double)r) * 8.0));
|
||||
}
|
||||
|
||||
void DrawCircleSteps(int x, int y, int r, int steps)
|
||||
{
|
||||
// Circles look better when offset negatively by half a pixel w/o MSAA
|
||||
const double fx = (antialias ? (double)x : (double)x - 0.5f) * scaleWidth;
|
||||
const double fy = (antialias ? (double)y : (double)y - 0.5f) * scaleHeight;
|
||||
|
||||
const double stepsz = (double)TAU / (double)steps;
|
||||
const double magw = (double)r * scaleWidth;
|
||||
const double magh = (double)r * scaleHeight;
|
||||
|
||||
glBegin(GL_LINE_LOOP);
|
||||
GlColour();
|
||||
glVertex2d(fx + magw, fy);
|
||||
for (int i = 1; i < steps; ++i)
|
||||
{
|
||||
const double theta = stepsz * (double)i;
|
||||
double ofsx = cos(theta) * magw;
|
||||
double ofsy = sin(theta) * magh;
|
||||
glVertex2d(fx + ofsx, fy - ofsy);
|
||||
}
|
||||
glEnd();
|
||||
}
|
||||
|
||||
void DrawPresent(void)
|
||||
{
|
||||
SDL_GL_SwapWindow(window);
|
||||
}
|
Loading…
Reference in New Issue
Block a user