ref, feat: Restructure
- The renderer backend is now its own library, loaded at runtime. - Removed GLFW dependency, instead use win32 directly. - Broke linux window creation, because it's not implemented yet. - Maybe use GLFW for linux?
This commit is contained in:
		
							parent
							
								
									63e3f973b2
								
							
						
					
					
						commit
						81798df3e9
					
				@ -1,60 +0,0 @@
 | 
				
			|||||||
#ifndef VY_FIO_H
 | 
					 | 
				
			||||||
#define VY_FIO_H
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include <stdbool.h>
 | 
					 | 
				
			||||||
#include <stddef.h>
 | 
					 | 
				
			||||||
#include <stdint.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include "voyage.h"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
enum
 | 
					 | 
				
			||||||
{
 | 
					 | 
				
			||||||
    VY_FILE_BUFFER_FLAG_FILE_NOT_FOUND = 0x1,
 | 
					 | 
				
			||||||
    VY_FILE_BUFFER_FLAG_READ_FAILED    = 0x2,
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef struct {
 | 
					 | 
				
			||||||
    void *data;
 | 
					 | 
				
			||||||
    size_t size;
 | 
					 | 
				
			||||||
    uint32_t flags;
 | 
					 | 
				
			||||||
} vy_file_buffer;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
inline bool vyWasFileBufferSuccessful(const vy_file_buffer *fb) {
 | 
					 | 
				
			||||||
    return fb->flags == 0;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* used to identify a file (XXH3 hash of the path) */
 | 
					 | 
				
			||||||
typedef uint64_t vy_file_id;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef unsigned int vy_fio_handle;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef struct {
 | 
					 | 
				
			||||||
    unsigned int queue_size;
 | 
					 | 
				
			||||||
    unsigned int max_file_count;
 | 
					 | 
				
			||||||
} vy_fio_config;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyInitFIO(const vy_fio_config *config);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
void vyShutdownFIO(void);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_file_id vyGetFileId(const char *path);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_file_id vyGetFileIdFromSpan(vy_text_span path);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_file_id vyAddFile(const char *path);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_file_id vyAddFileFromSpan(vy_text_span path);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
const char *vyGetFilePath(vy_file_id fid);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_fio_handle vyEnqueueRead(vy_file_id fid);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
void vyAbortFIO(vy_fio_handle fio);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyIsFIOFinished(vy_fio_handle fio);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyRetrieveReadBuffer(vy_fio_handle fio, vy_file_buffer *buffer);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
void vyFreeFileBuffer(vy_file_buffer buffer);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
@ -1,29 +0,0 @@
 | 
				
			|||||||
#ifndef VY_GFX_BACKEND_H
 | 
					 | 
				
			||||||
#define VY_GFX_BACKEND_H
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* Backend functions and types. */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include <stddef.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include "gfx.h"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef struct {
 | 
					 | 
				
			||||||
    const char *compute_source;
 | 
					 | 
				
			||||||
    size_t compute_source_length;
 | 
					 | 
				
			||||||
} vy_compute_pipeline_info;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef struct {
 | 
					 | 
				
			||||||
    const char *vertex_source;
 | 
					 | 
				
			||||||
    size_t vertex_source_length;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    const char *fragment_source;
 | 
					 | 
				
			||||||
    size_t fragment_source_length;
 | 
					 | 
				
			||||||
} vy_graphics_pipeline_info;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_gfx_pipeline_id
 | 
					 | 
				
			||||||
vyCompileComputePipeline(const vy_compute_pipeline_info *info);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_gfx_pipeline_id
 | 
					 | 
				
			||||||
vyCompileGraphicsPipeline(const vy_graphics_pipeline_info *info);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
@ -1,18 +0,0 @@
 | 
				
			|||||||
#ifndef VY_THREADING_H
 | 
					 | 
				
			||||||
#define VY_THREADING_H
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* platform independent threading */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include <stdbool.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef struct vy_mutex_s vy_mutex;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
vy_mutex *vyCreateMutex(void);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
void vyDestroyMutex(vy_mutex *mutex);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyLockMutex(vy_mutex *mutex);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyUnlockMutex(vy_mutex *mutex);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
							
								
								
									
										74
									
								
								meson.build
									
									
									
									
									
								
							
							
						
						
									
										74
									
								
								meson.build
									
									
									
									
									
								
							@ -22,42 +22,64 @@ elif compiler.get_argument_syntax() == 'msvc'
 | 
				
			|||||||
endif
 | 
					endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
# Debug specific flags
 | 
					# Debug specific flags
 | 
				
			||||||
if buildtype == 'debug'
 | 
					if buildtype == 'debug' or buildtype == 'debugoptimized'
 | 
				
			||||||
  add_project_arguments([ '-DDEBUG'], language : 'c')
 | 
					  add_project_arguments([ '-DDEBUG'], language : 'c')
 | 
				
			||||||
endif
 | 
					endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
# "Select" renderer backend
 | 
					 | 
				
			||||||
# Currently only OpenGL is supported
 | 
					 | 
				
			||||||
add_project_arguments([ '-DRENDERER_GL'], language : 'c')
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
# Gather dependencies
 | 
					# Gather dependencies
 | 
				
			||||||
thread_dep = dependency('threads')
 | 
					thread_dep = dependency('threads')
 | 
				
			||||||
m_dep = compiler.find_library('m', required : false)
 | 
					m_dep = compiler.find_library('m', required : false)
 | 
				
			||||||
glfw_proj = subproject('glfw', default_options : 'default_library=static')
 | 
					vk_dep = dependency('vulkan', required : false)
 | 
				
			||||||
glfw_dep = glfw_proj.get_variable('glfw_dep')
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
incdir = include_directories(['contrib', 'include'])
 | 
					# glfw_proj = subproject('glfw', default_options : 'default_library=static')
 | 
				
			||||||
 | 
					# glfw_dep = glfw_proj.get_variable('glfw_dep')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
executable('voyage',
 | 
					incdir = include_directories(['contrib', 'src'])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					runtime_lib = library('vyrt',
 | 
				
			||||||
  # Project Sources
 | 
					  # Project Sources
 | 
				
			||||||
  'include/voyage.h',
 | 
					  'src/runtime/runtime.h',
 | 
				
			||||||
  'include/gfx.h',
 | 
					  'src/runtime/gfx.h',
 | 
				
			||||||
  'include/gfx_backend.h',
 | 
					  'src/runtime/renderer_api.h',
 | 
				
			||||||
  'include/fio.h',
 | 
					  'src/runtime/fio.h',
 | 
				
			||||||
  'include/config.h',
 | 
					  'src/runtime/config.h',
 | 
				
			||||||
  'include/threading.h',
 | 
					  'src/runtime/threading.h',
 | 
				
			||||||
 | 
					  'src/runtime/app.h',
 | 
				
			||||||
 | 
					  'src/runtime/dynamic_libs.h',
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  'src/voyage.c',
 | 
					  'src/runtime/error_report.c',
 | 
				
			||||||
  'src/fio.c',
 | 
					  'src/runtime/gfx_main.c',
 | 
				
			||||||
  'src/error_report.c',
 | 
					  'src/runtime/gfx_shader_loading.c',
 | 
				
			||||||
  'src/gfx_main.c',
 | 
					  'src/runtime/config.c',
 | 
				
			||||||
  'src/gfx_shader_loading.c',
 | 
					  'src/runtime/runtime_cvars.c',
 | 
				
			||||||
  'src/gfx_pipelines.c',
 | 
					  'src/runtime/threading.c',
 | 
				
			||||||
  'src/config.c',
 | 
					  'src/runtime/fio.c',
 | 
				
			||||||
  'src/threading.c',
 | 
					  'src/runtime/app.c',
 | 
				
			||||||
 | 
					  'src/runtime/dynamic_libs.c',
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  # Contrib Sources
 | 
					  # Contrib Sources
 | 
				
			||||||
  'contrib/glad/glad.c',
 | 
					 | 
				
			||||||
  'contrib/xxhash/xxhash.c',
 | 
					  'contrib/xxhash/xxhash.c',
 | 
				
			||||||
  dependencies : [thread_dep, m_dep, glfw_dep],
 | 
					  dependencies : [thread_dep, m_dep],
 | 
				
			||||||
  include_directories: incdir)
 | 
					  include_directories : incdir,
 | 
				
			||||||
 | 
					  c_pch : 'pch/rt_pch.h')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if vk_dep.found()
 | 
				
			||||||
 | 
					  vk_renderer_lib = library('vyvk',
 | 
				
			||||||
 | 
					    # Project Sources
 | 
				
			||||||
 | 
					    'src/renderer/vk/gpu.h',
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    'src/renderer/vk/init.c',
 | 
				
			||||||
 | 
					    'src/renderer/vk/gfx_pipelines.c',
 | 
				
			||||||
 | 
					    dependencies : [m_dep, vk_dep],
 | 
				
			||||||
 | 
					    include_directories : incdir,
 | 
				
			||||||
 | 
					    link_with : [runtime_lib],
 | 
				
			||||||
 | 
					    c_pch : 'pch/vk_pch.h')
 | 
				
			||||||
 | 
					endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					executable('voyage',
 | 
				
			||||||
 | 
					  'src/game/voyage.c',
 | 
				
			||||||
 | 
					  include_directories : incdir,
 | 
				
			||||||
 | 
					  link_with : [runtime_lib],
 | 
				
			||||||
 | 
					  win_subsystem : 'windows')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										1
									
								
								pch/rt_pch.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1
									
								
								pch/rt_pch.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1 @@
 | 
				
			|||||||
 | 
					#include <Windows.h>
 | 
				
			||||||
							
								
								
									
										1
									
								
								pch/vk_pch.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1
									
								
								pch/vk_pch.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1 @@
 | 
				
			|||||||
 | 
					#include <vulkan/vulkan.h>
 | 
				
			||||||
							
								
								
									
										15
									
								
								src/game/voyage.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										15
									
								
								src/game/voyage.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,15 @@
 | 
				
			|||||||
 | 
					#include "runtime/app.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define WIN32_LEAN_AND_MEAN
 | 
				
			||||||
 | 
					#include <Windows.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					int WINAPI wWinMain(HINSTANCE hInstance,
 | 
				
			||||||
 | 
					                    HINSTANCE hPrevInstance,
 | 
				
			||||||
 | 
					                    PWSTR pCmdLine,
 | 
				
			||||||
 | 
					                    int nCmdShow) {
 | 
				
			||||||
 | 
					    return vyWin32Entry(hInstance, hPrevInstance, pCmdLine, nCmdShow);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
@ -1,23 +0,0 @@
 | 
				
			|||||||
#include <glad/glad.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include "gfx.h"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* Attributes are used to bind buffers (or textures) to symbolic values.
 | 
					 | 
				
			||||||
 * For example, an attribute might be bound to "CELL_GRID", which would be
 | 
					 | 
				
			||||||
 * replaced with the (at the time of the invoke) grid buffer of the current
 | 
					 | 
				
			||||||
 * world cell.
 | 
					 | 
				
			||||||
 */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyLoadShaders(const char **paths, vy_shader *shaders, unsigned int count);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
bool vyInitRenderer(void) {
 | 
					 | 
				
			||||||
    /* Init shader programs */
 | 
					 | 
				
			||||||
    const char *shader_files[] = {"shader/cell.shader"};
 | 
					 | 
				
			||||||
    vy_shader shaders[1];
 | 
					 | 
				
			||||||
    if (!vyLoadShaders(shader_files, shaders, 1))
 | 
					 | 
				
			||||||
        return false;
 | 
					 | 
				
			||||||
    return true;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
void vyShutdownRenderer(void) {
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
@ -1,11 +1,11 @@
 | 
				
			|||||||
#include <glad/glad.h>
 | 
					#include "runtime/runtime.h"
 | 
				
			||||||
 | 
					#include "runtime/gfx.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include "gfx.h"
 | 
					#include "runtime/renderer_api.h"
 | 
				
			||||||
#include "gfx_backend.h"
 | 
					 | 
				
			||||||
#include "voyage.h"
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
typedef struct {
 | 
					typedef struct {
 | 
				
			||||||
    GLuint prog;
 | 
					
 | 
				
			||||||
 | 
					    unsigned int prog;
 | 
				
			||||||
} vy_gl_pipeline;
 | 
					} vy_gl_pipeline;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define NUM_SLOTS 256
 | 
					#define NUM_SLOTS 256
 | 
				
			||||||
@ -52,8 +52,9 @@ static void ReleasePipelineSlot(vy_gfx_pipeline_id id) {
 | 
				
			|||||||
        _storage.generation_in_use[slot] &= ~0x1;
 | 
					        _storage.generation_in_use[slot] &= ~0x1;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_gfx_pipeline_id
 | 
					VY_DLLEXPORT vy_gfx_pipeline_id
 | 
				
			||||||
vyCompileComputePipeline(const vy_compute_pipeline_info *info) {
 | 
					vyCompileComputePipeline(const vy_compute_pipeline_info *info) {
 | 
				
			||||||
 | 
					#if 0
 | 
				
			||||||
    char info_log[512];
 | 
					    char info_log[512];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    GLuint prog   = glCreateProgram();
 | 
					    GLuint prog   = glCreateProgram();
 | 
				
			||||||
@ -86,16 +87,18 @@ vyCompileComputePipeline(const vy_compute_pipeline_info *info) {
 | 
				
			|||||||
        return (vy_gfx_pipeline_id){0};
 | 
					        return (vy_gfx_pipeline_id){0};
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
    glDeleteShader(shader);
 | 
					    glDeleteShader(shader);
 | 
				
			||||||
 | 
					    #endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    vy_gl_pipeline pipeline;
 | 
					    vy_gl_pipeline pipeline;
 | 
				
			||||||
    pipeline.prog = prog;
 | 
					    pipeline.prog = 0;
 | 
				
			||||||
    return StorePipeline(pipeline);
 | 
					    return StorePipeline(pipeline);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_gfx_pipeline_id
 | 
					VY_DLLEXPORT vy_gfx_pipeline_id
 | 
				
			||||||
vyCompileGraphicsPipeline(const vy_graphics_pipeline_info *info) {
 | 
					vyCompileGraphicsPipeline(const vy_graphics_pipeline_info *info) {
 | 
				
			||||||
    char info_log[512];
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    #if 0
 | 
				
			||||||
 | 
					    char info_log[512];
 | 
				
			||||||
    GLuint prog            = glCreateProgram();
 | 
					    GLuint prog            = glCreateProgram();
 | 
				
			||||||
    GLuint vertex_shader   = glCreateShader(GL_VERTEX_SHADER);
 | 
					    GLuint vertex_shader   = glCreateShader(GL_VERTEX_SHADER);
 | 
				
			||||||
    GLuint fragment_shader = glCreateShader(GL_FRAGMENT_SHADER);
 | 
					    GLuint fragment_shader = glCreateShader(GL_FRAGMENT_SHADER);
 | 
				
			||||||
@ -148,8 +151,9 @@ vyCompileGraphicsPipeline(const vy_graphics_pipeline_info *info) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
    glDeleteShader(vertex_shader);
 | 
					    glDeleteShader(vertex_shader);
 | 
				
			||||||
    glDeleteShader(fragment_shader);
 | 
					    glDeleteShader(fragment_shader);
 | 
				
			||||||
 | 
					    #endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    vy_gl_pipeline pipeline;
 | 
					    vy_gl_pipeline pipeline;
 | 
				
			||||||
    pipeline.prog = prog;
 | 
					    pipeline.prog = 0;
 | 
				
			||||||
    return StorePipeline(pipeline);
 | 
					    return StorePipeline(pipeline);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
							
								
								
									
										15
									
								
								src/renderer/vk/gpu.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										15
									
								
								src/renderer/vk/gpu.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,15 @@
 | 
				
			|||||||
 | 
					#ifndef VY_VK_GPU_H
 | 
				
			||||||
 | 
					#define VY_VK_GPU_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <vulkan/vulkan.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    VkInstance instance;
 | 
				
			||||||
 | 
					    VkAllocationCallbacks *alloc_cb;
 | 
				
			||||||
 | 
					} vy_vk_gpu;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifndef VY_VK_DONT_DEFINE_GPU_GLOBAL
 | 
				
			||||||
 | 
					extern vy_vk_gpu g_gpu;
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
							
								
								
									
										137
									
								
								src/renderer/vk/init.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										137
									
								
								src/renderer/vk/init.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,137 @@
 | 
				
			|||||||
 | 
					#include <stdlib.h>
 | 
				
			||||||
 | 
					#include <malloc.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define VY_VK_DONT_DEFINE_GPU_GLOBAL
 | 
				
			||||||
 | 
					#include "gpu.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime/runtime.h"
 | 
				
			||||||
 | 
					#include "runtime/renderer_api.h"
 | 
				
			||||||
 | 
					#include "runtime/config.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_CVAR_I(r_EnableAPIAllocTracking,
 | 
				
			||||||
 | 
					          "Enable tracking of allocations done by the vulkan api. [0/1] Default: 0",
 | 
				
			||||||
 | 
					          0);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    size_t allocated;
 | 
				
			||||||
 | 
					    size_t reallocated;
 | 
				
			||||||
 | 
					    size_t freed;
 | 
				
			||||||
 | 
					    size_t max_alignment;
 | 
				
			||||||
 | 
					} vy_vk_alloc_stats;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					vy_vk_gpu g_gpu;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static VkAllocationCallbacks _tracking_alloc_cbs;
 | 
				
			||||||
 | 
					static vy_vk_alloc_stats _alloc_stats;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static const char *AllocationScopeToString(VkSystemAllocationScope scope)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					    switch (scope) {
 | 
				
			||||||
 | 
					    case VK_SYSTEM_ALLOCATION_SCOPE_COMMAND:
 | 
				
			||||||
 | 
					        return "COMMAND";
 | 
				
			||||||
 | 
					    case VK_SYSTEM_ALLOCATION_SCOPE_OBJECT:
 | 
				
			||||||
 | 
					        return "OBJECT";
 | 
				
			||||||
 | 
					    case VK_SYSTEM_ALLOCATION_SCOPE_CACHE:
 | 
				
			||||||
 | 
					        return "CACHE";
 | 
				
			||||||
 | 
					    case VK_SYSTEM_ALLOCATION_SCOPE_DEVICE:
 | 
				
			||||||
 | 
					        return "DEVICE";
 | 
				
			||||||
 | 
					    case VK_SYSTEM_ALLOCATION_SCOPE_INSTANCE:
 | 
				
			||||||
 | 
					        return "INSTANCE";
 | 
				
			||||||
 | 
					    default:
 | 
				
			||||||
 | 
					        return "UNKNOWN";
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void LogAllocationStats(const vy_vk_alloc_stats *stats) {
 | 
				
			||||||
 | 
					    vyLog("vk",
 | 
				
			||||||
 | 
					          "Allocated: %zu bytes. Reallocated: %zu bytes. Max. requested "
 | 
				
			||||||
 | 
					          "alignment: %zu bytes",
 | 
				
			||||||
 | 
					          stats->allocated,
 | 
				
			||||||
 | 
					          stats->reallocated,
 | 
				
			||||||
 | 
					          stats->max_alignment);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void *TrackAllocation(void *userData, size_t size, size_t alignment, VkSystemAllocationScope scope) {
 | 
				
			||||||
 | 
					    vy_vk_alloc_stats *stats = userData;
 | 
				
			||||||
 | 
					    if (alignment > stats->max_alignment)
 | 
				
			||||||
 | 
					        stats->max_alignment = alignment;
 | 
				
			||||||
 | 
					    stats->allocated += size;
 | 
				
			||||||
 | 
					    vyLog("vk",
 | 
				
			||||||
 | 
					          "Allocation. Size: %zu, Alignment: %zu, Scope: %s",
 | 
				
			||||||
 | 
					          size,
 | 
				
			||||||
 | 
					          alignment,
 | 
				
			||||||
 | 
					          AllocationScopeToString(scope));
 | 
				
			||||||
 | 
					    LogAllocationStats(stats);
 | 
				
			||||||
 | 
					    return _aligned_malloc(size, alignment);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void *TrackReallocation(void *userData,
 | 
				
			||||||
 | 
					                               void *original,
 | 
				
			||||||
 | 
					                               size_t size,
 | 
				
			||||||
 | 
					                               size_t alignment,
 | 
				
			||||||
 | 
					                               VkSystemAllocationScope scope) {
 | 
				
			||||||
 | 
					    vy_vk_alloc_stats *stats = userData;
 | 
				
			||||||
 | 
					    if (alignment > stats->max_alignment)
 | 
				
			||||||
 | 
					        stats->max_alignment = alignment;
 | 
				
			||||||
 | 
					    stats->reallocated += size;
 | 
				
			||||||
 | 
					    vyLog("vk",
 | 
				
			||||||
 | 
					          "Reallocation. Size: %zu, Alignment: %zu, Scope: %s",
 | 
				
			||||||
 | 
					          size,
 | 
				
			||||||
 | 
					          alignment,
 | 
				
			||||||
 | 
					          AllocationScopeToString(scope));
 | 
				
			||||||
 | 
					    LogAllocationStats(stats);
 | 
				
			||||||
 | 
					    return _aligned_realloc(original, size, alignment);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void TrackFree(void *userData, void *memory) {
 | 
				
			||||||
 | 
					    vy_vk_alloc_stats *stats = userData;
 | 
				
			||||||
 | 
					    vyLog("vk", "Free.");
 | 
				
			||||||
 | 
					    LogAllocationStats(stats);
 | 
				
			||||||
 | 
					    free(memory);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT int vyInit(const vy_renderer_init_info *info) {
 | 
				
			||||||
 | 
					    vyLog("vk", "Init");
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    vyRegisterCVAR(&r_EnableAPIAllocTracking);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    _tracking_alloc_cbs.pUserData = &_alloc_stats;
 | 
				
			||||||
 | 
					    _tracking_alloc_cbs.pfnAllocation = TrackAllocation;
 | 
				
			||||||
 | 
					    _tracking_alloc_cbs.pfnReallocation = TrackReallocation;
 | 
				
			||||||
 | 
					    _tracking_alloc_cbs.pfnFree         = TrackFree;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (r_EnableAPIAllocTracking.i) {
 | 
				
			||||||
 | 
					        g_gpu.alloc_cb = &_tracking_alloc_cbs;
 | 
				
			||||||
 | 
					    } else {
 | 
				
			||||||
 | 
					        g_gpu.alloc_cb = NULL;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    VkResult result;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    VkApplicationInfo app_info = {
 | 
				
			||||||
 | 
					        .apiVersion = VK_API_VERSION_1_0,
 | 
				
			||||||
 | 
					        .applicationVersion = 0x00001000,
 | 
				
			||||||
 | 
					        .engineVersion = 0x00001000,
 | 
				
			||||||
 | 
					        .pEngineName = "voyage",
 | 
				
			||||||
 | 
					        .pApplicationName = "Voyage",
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    VkInstanceCreateInfo instance_info = {
 | 
				
			||||||
 | 
					        .sType            = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO,
 | 
				
			||||||
 | 
					        .pApplicationInfo = &app_info,
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    result = vkCreateInstance(&instance_info, g_gpu.alloc_cb, &g_gpu.instance);
 | 
				
			||||||
 | 
					    if (result != VK_SUCCESS) {
 | 
				
			||||||
 | 
					        vyReportError("vk", "Failed to create the vulkan instance!");
 | 
				
			||||||
 | 
					        return 1;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return 0;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyShutdown(void) {
 | 
				
			||||||
 | 
					    vyLog("vk", "Shutdown");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    vkDestroyInstance(g_gpu.instance, g_gpu.alloc_cb);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
							
								
								
									
										130
									
								
								src/runtime/app.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										130
									
								
								src/runtime/app.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,130 @@
 | 
				
			|||||||
 | 
					#include "app.h"
 | 
				
			||||||
 | 
					#include "fio.h"
 | 
				
			||||||
 | 
					#include "gfx.h"
 | 
				
			||||||
 | 
					#include "config.h"
 | 
				
			||||||
 | 
					#include "renderer_api.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern void __RegisterRuntimeCVars(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_CVAR_I(rt_Fullscreen, "Show window in fullscreen mode. [0/1] Default: 0", 0);
 | 
				
			||||||
 | 
					VY_CVAR_I(rt_WindowWidth, "Window width. Default: 1024", 1024);
 | 
				
			||||||
 | 
					VY_CVAR_I(rt_WindowHeight, "Window height. Default: 768", 768);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					#define WIN32_LEAN_AND_MEAN
 | 
				
			||||||
 | 
					#include <Windows.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static LRESULT CALLBACK win32WndProc(HWND hWnd,
 | 
				
			||||||
 | 
					                                     UINT uMsg,
 | 
				
			||||||
 | 
					                                     WPARAM wParam,
 | 
				
			||||||
 | 
					                                     LPARAM lParam) {
 | 
				
			||||||
 | 
					    switch (uMsg) {
 | 
				
			||||||
 | 
					    case WM_CLOSE: 
 | 
				
			||||||
 | 
					        PostQuitMessage(0);
 | 
				
			||||||
 | 
					        return 0;
 | 
				
			||||||
 | 
					    default:
 | 
				
			||||||
 | 
					        return DefWindowProcW(hWnd, uMsg, wParam, lParam);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT int vyWin32Entry(HINSTANCE hInstance,
 | 
				
			||||||
 | 
					    HINSTANCE hPrevInstance,
 | 
				
			||||||
 | 
					    PWSTR pCmdLine,
 | 
				
			||||||
 | 
					    int nCmdShow) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    __RegisterRuntimeCVars();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    vy_fio_config fio_config = {0};
 | 
				
			||||||
 | 
					    if (!vyInitFIO(&fio_config)) {
 | 
				
			||||||
 | 
					        vyReportError("FIO", "Init failed.");
 | 
				
			||||||
 | 
					        return 1;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    WNDCLASSEXW wndclass = {
 | 
				
			||||||
 | 
					        .cbSize        = sizeof(wndclass),
 | 
				
			||||||
 | 
					        .hInstance     = hInstance,
 | 
				
			||||||
 | 
					        .lpszClassName = L"vyWndClass",
 | 
				
			||||||
 | 
					        .style         = CS_OWNDC,
 | 
				
			||||||
 | 
					        .lpfnWndProc   = win32WndProc,
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    if (!RegisterClassExW(&wndclass)) {
 | 
				
			||||||
 | 
					        vyReportError("CORE", "RegisterClassEx failed: %u", GetLastError());
 | 
				
			||||||
 | 
					        return 1;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    HWND wnd = NULL; 
 | 
				
			||||||
 | 
					    if (rt_Fullscreen.i) {
 | 
				
			||||||
 | 
					        /* Fullscreen window */
 | 
				
			||||||
 | 
					        int w    = GetSystemMetrics(SM_CXSCREEN);
 | 
				
			||||||
 | 
					        int h    = GetSystemMetrics(SM_CYSCREEN);
 | 
				
			||||||
 | 
					        wnd      = CreateWindowExW(WS_EX_APPWINDOW,
 | 
				
			||||||
 | 
					                              L"vyWndClass",
 | 
				
			||||||
 | 
					                              L"Voyage",
 | 
				
			||||||
 | 
					                              WS_POPUP,
 | 
				
			||||||
 | 
					                              0,
 | 
				
			||||||
 | 
					                              0,
 | 
				
			||||||
 | 
					                              w,
 | 
				
			||||||
 | 
					                              h,
 | 
				
			||||||
 | 
					                              NULL,
 | 
				
			||||||
 | 
					                              NULL,
 | 
				
			||||||
 | 
					                              hInstance,
 | 
				
			||||||
 | 
					                              NULL);
 | 
				
			||||||
 | 
					        ShowWindow(wnd, SW_SHOW);
 | 
				
			||||||
 | 
					    } else {
 | 
				
			||||||
 | 
					        /* Windowed mode */
 | 
				
			||||||
 | 
					        int w = rt_WindowWidth.i;
 | 
				
			||||||
 | 
					        int h = rt_WindowHeight.i;
 | 
				
			||||||
 | 
					        wnd   = CreateWindowExW(WS_EX_APPWINDOW,
 | 
				
			||||||
 | 
					                              L"vyWndClass",
 | 
				
			||||||
 | 
					                              L"Voyage",
 | 
				
			||||||
 | 
					                              WS_OVERLAPPED | WS_CAPTION | WS_SYSMENU,
 | 
				
			||||||
 | 
					                              CW_USEDEFAULT,
 | 
				
			||||||
 | 
					                              CW_USEDEFAULT,
 | 
				
			||||||
 | 
					                              w,
 | 
				
			||||||
 | 
					                              h,
 | 
				
			||||||
 | 
					                              NULL,
 | 
				
			||||||
 | 
					                              NULL,
 | 
				
			||||||
 | 
					                              hInstance,
 | 
				
			||||||
 | 
					                              NULL);
 | 
				
			||||||
 | 
					        ShowWindow(wnd, SW_SHOW);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (!wnd) {
 | 
				
			||||||
 | 
					        vyReportError("CORE",
 | 
				
			||||||
 | 
					                      "Failed to create the game window: %u",
 | 
				
			||||||
 | 
					                      GetLastError());
 | 
				
			||||||
 | 
					        return 1;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    vy_renderer_init_info renderer_info = {.hWnd = wnd, .hInstance = hInstance};
 | 
				
			||||||
 | 
					    if (!vyInitGFX(&renderer_info)) {
 | 
				
			||||||
 | 
					        vyReportError("GFX", "Init failed.");
 | 
				
			||||||
 | 
					        return 1;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    /* Main Loop */
 | 
				
			||||||
 | 
					    bool keep_running = true;
 | 
				
			||||||
 | 
					    while (keep_running) {
 | 
				
			||||||
 | 
					        MSG msg;
 | 
				
			||||||
 | 
					        while (PeekMessageW(&msg, NULL, 0, 0, PM_REMOVE)) {
 | 
				
			||||||
 | 
					            if (msg.message == WM_QUIT) {
 | 
				
			||||||
 | 
					                keep_running = false;
 | 
				
			||||||
 | 
					            } else {
 | 
				
			||||||
 | 
					                TranslateMessage(&msg);
 | 
				
			||||||
 | 
					                DispatchMessageW(&msg);
 | 
				
			||||||
 | 
					            }
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    vyShutdownGFX();
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    DestroyWindow(wnd);
 | 
				
			||||||
 | 
					    UnregisterClassW(L"vyWndClass", hInstance);
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    vyShutdownFIO();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return 0;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
							
								
								
									
										20
									
								
								src/runtime/app.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										20
									
								
								src/runtime/app.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,20 @@
 | 
				
			|||||||
 | 
					#ifndef VY_APP_H
 | 
				
			||||||
 | 
					#define VY_APP_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Platform specific application entry point */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Forward declared here, to avoid including windows.h */
 | 
				
			||||||
 | 
					struct HINSTANCE__;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT int vyWin32Entry(struct HINSTANCE__ *hInstance,
 | 
				
			||||||
 | 
					                 struct HINSTANCE__ *hPrevInstance,
 | 
				
			||||||
 | 
					                 wchar_t *pCmdLine,
 | 
				
			||||||
 | 
					                 int nCmdShow);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
@ -1,6 +1,6 @@
 | 
				
			|||||||
#include "config.h"
 | 
					#include "config.h"
 | 
				
			||||||
#include "threading.h"
 | 
					#include "threading.h"
 | 
				
			||||||
#include "voyage.h"
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include <stddef.h>
 | 
					#include <stddef.h>
 | 
				
			||||||
#include <string.h>
 | 
					#include <string.h>
 | 
				
			||||||
@ -1,6 +1,8 @@
 | 
				
			|||||||
#ifndef VY_CONFIG_H
 | 
					#ifndef VY_CONFIG_H
 | 
				
			||||||
#define VY_CONFIG_H
 | 
					#define VY_CONFIG_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
typedef enum
 | 
					typedef enum
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
    VY_CVAR_TYPE_INT,
 | 
					    VY_CVAR_TYPE_INT,
 | 
				
			||||||
@ -36,8 +38,8 @@ typedef struct
 | 
				
			|||||||
                 .s           = (v),                                           \
 | 
					                 .s           = (v),                                           \
 | 
				
			||||||
                 .type        = VY_CVAR_TYPE_STRING}
 | 
					                 .type        = VY_CVAR_TYPE_STRING}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyRegisterCVAR(vy_cvar *cvar);
 | 
					VY_DLLEXPORT void vyRegisterCVAR(vy_cvar *cvar);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_cvar *vyGetCVAR(const char *name);
 | 
					VY_DLLEXPORT vy_cvar *vyGetCVAR(const char *name);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
							
								
								
									
										43
									
								
								src/runtime/dynamic_libs.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										43
									
								
								src/runtime/dynamic_libs.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,43 @@
 | 
				
			|||||||
 | 
					#include "dynamic_libs.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					#define WIN32_LEAN_AND_MEAN
 | 
				
			||||||
 | 
					#include <Windows.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_dynlib vyOpenLib(const char *libname) {
 | 
				
			||||||
 | 
					    wchar_t libname_w[MAX_PATH];
 | 
				
			||||||
 | 
					    MultiByteToWideChar(CP_UTF8,
 | 
				
			||||||
 | 
					                        MB_PRECOMPOSED,
 | 
				
			||||||
 | 
					                        libname,
 | 
				
			||||||
 | 
					                        -1,
 | 
				
			||||||
 | 
					                        libname_w,
 | 
				
			||||||
 | 
					                        MAX_PATH);
 | 
				
			||||||
 | 
					    HMODULE mod = LoadLibraryW(libname_w);
 | 
				
			||||||
 | 
					    return (vy_dynlib)mod;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void *vyGetSymbol(vy_dynlib lib, const char *symbol) {
 | 
				
			||||||
 | 
					    return (void*)GetProcAddress((HMODULE)lib, symbol);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyCloseLib(vy_dynlib lib) {
 | 
				
			||||||
 | 
					    FreeLibrary((HMODULE)lib);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#elif defined(__linux__)
 | 
				
			||||||
 | 
					#include <dlfcn.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_dynlib vyOpenLib(const char *libname) {
 | 
				
			||||||
 | 
					    return dlopen(libname, RTLD_NOW | RTLD_LOCAL);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void *vyGetSymbol(vy_dynlib lib, const char *symbol) {
 | 
				
			||||||
 | 
					    return dlsym(lib, symbol);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyCloseLib(vy_dynlib lib) {
 | 
				
			||||||
 | 
					    dlclose(lib);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
							
								
								
									
										20
									
								
								src/runtime/dynamic_libs.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										20
									
								
								src/runtime/dynamic_libs.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,20 @@
 | 
				
			|||||||
 | 
					#ifndef VY_DYNAMIC_LIBS_H
 | 
				
			||||||
 | 
					#define VY_DYNAMIC_LIBS_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					    #define VY_DLLNAME(s) (s".dll")
 | 
				
			||||||
 | 
					#elif defined(__linux__)
 | 
				
			||||||
 | 
					    #define VY_DLLNAME(s) ("lib"s".so")
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef void *vy_dynlib;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_dynlib vyOpenLib(const char *libname);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void *vyGetSymbol(vy_dynlib lib, const char *symbol);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyCloseLib(vy_dynlib lib);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
@ -1,7 +1,7 @@
 | 
				
			|||||||
#include <stdarg.h>
 | 
					#include <stdarg.h>
 | 
				
			||||||
#include <stdio.h>
 | 
					#include <stdio.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include "voyage.h"
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#ifdef _WIN32
 | 
					#ifdef _WIN32
 | 
				
			||||||
#define WIN32_LEAN_AND_MEAN
 | 
					#define WIN32_LEAN_AND_MEAN
 | 
				
			||||||
@ -40,7 +40,7 @@ static void LogOut(const char *text)
 | 
				
			|||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyReportError(const char *subsystem, const char *fmt, ...) {
 | 
					VY_DLLEXPORT void vyReportError(const char *subsystem, const char *fmt, ...) {
 | 
				
			||||||
    char buf[256];
 | 
					    char buf[256];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    int at = snprintf(buf, VY_ARRAY_COUNT(buf) - 1, "[%s] ", subsystem);
 | 
					    int at = snprintf(buf, VY_ARRAY_COUNT(buf) - 1, "[%s] ", subsystem);
 | 
				
			||||||
@ -54,7 +54,7 @@ void vyReportError(const char *subsystem, const char *fmt, ...) {
 | 
				
			|||||||
    DisplayErrorBox(buf);
 | 
					    DisplayErrorBox(buf);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyLog(const char *subsystem, const char *fmt, ...) {
 | 
					VY_DLLEXPORT void vyLog(const char *subsystem, const char *fmt, ...) {
 | 
				
			||||||
    char buf[256];
 | 
					    char buf[256];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    int at = snprintf(buf, VY_ARRAY_COUNT(buf) - 1, "[%s] ", subsystem);
 | 
					    int at = snprintf(buf, VY_ARRAY_COUNT(buf) - 1, "[%s] ", subsystem);
 | 
				
			||||||
@ -139,7 +139,7 @@ static void *linuxFIOThreadProc(void *);
 | 
				
			|||||||
static DWORD WINAPI win32FIOThreadProc(_In_ LPVOID);
 | 
					static DWORD WINAPI win32FIOThreadProc(_In_ LPVOID);
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyInitFIO(const vy_fio_config *config) {
 | 
					VY_DLLEXPORT bool vyInitFIO(const vy_fio_config *config) {
 | 
				
			||||||
    unsigned int queue_size = (config->queue_size) ? config->queue_size : 512;
 | 
					    unsigned int queue_size = (config->queue_size) ? config->queue_size : 512;
 | 
				
			||||||
    unsigned int max_file_count =
 | 
					    unsigned int max_file_count =
 | 
				
			||||||
        (config->max_file_count) ? config->max_file_count : 512;
 | 
					        (config->max_file_count) ? config->max_file_count : 512;
 | 
				
			||||||
@ -165,7 +165,7 @@ bool vyInitFIO(const vy_fio_config *config) {
 | 
				
			|||||||
    return true;
 | 
					    return true;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyShutdownFIO(void) {
 | 
					VY_DLLEXPORT void vyShutdownFIO(void) {
 | 
				
			||||||
#ifdef __linux__
 | 
					#ifdef __linux__
 | 
				
			||||||
    pthread_cancel(_thread);
 | 
					    pthread_cancel(_thread);
 | 
				
			||||||
    pthread_join(_thread, NULL);
 | 
					    pthread_join(_thread, NULL);
 | 
				
			||||||
@ -199,7 +199,7 @@ vy_file_id vyGetFileIdFromSpan(vy_text_span path) {
 | 
				
			|||||||
    return fid;
 | 
					    return fid;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_file_id vyAddFileFromSpan(vy_text_span path) {
 | 
					VY_DLLEXPORT vy_file_id vyAddFileFromSpan(vy_text_span path) {
 | 
				
			||||||
    vy_file_id fid = vyGetFileIdFromSpan(path);
 | 
					    vy_file_id fid = vyGetFileIdFromSpan(path);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#ifdef __linux__
 | 
					#ifdef __linux__
 | 
				
			||||||
@ -246,14 +246,14 @@ vy_file_id vyAddFileFromSpan(vy_text_span path) {
 | 
				
			|||||||
    return fid;
 | 
					    return fid;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_file_id vyAddFile(const char *path) {
 | 
					VY_DLLEXPORT vy_file_id vyAddFile(const char *path) {
 | 
				
			||||||
    vy_text_span span;
 | 
					    vy_text_span span;
 | 
				
			||||||
    span.start  = path;
 | 
					    span.start  = path;
 | 
				
			||||||
    span.length = (unsigned int)strlen(path);
 | 
					    span.length = (unsigned int)strlen(path);
 | 
				
			||||||
    return vyAddFileFromSpan(span);
 | 
					    return vyAddFileFromSpan(span);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const char *vyGetFilePath(vy_file_id fid) {
 | 
					VY_DLLEXPORT const char *vyGetFilePath(vy_file_id fid) {
 | 
				
			||||||
    /* Hash Lookup */
 | 
					    /* Hash Lookup */
 | 
				
			||||||
    if (fid == 0)
 | 
					    if (fid == 0)
 | 
				
			||||||
        return NULL;
 | 
					        return NULL;
 | 
				
			||||||
@ -286,7 +286,7 @@ const char *vyGetFilePath(vy_file_id fid) {
 | 
				
			|||||||
    return result;
 | 
					    return result;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_fio_handle vyEnqueueRead(vy_file_id fid) {
 | 
					VY_DLLEXPORT vy_fio_handle vyEnqueueRead(vy_file_id fid) {
 | 
				
			||||||
    vy_fio_handle handle = 0;
 | 
					    vy_fio_handle handle = 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    do {
 | 
					    do {
 | 
				
			||||||
@ -326,7 +326,7 @@ vy_fio_handle vyEnqueueRead(vy_file_id fid) {
 | 
				
			|||||||
    return handle;
 | 
					    return handle;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyAbortFIO(vy_fio_handle fio) {
 | 
					VY_DLLEXPORT void vyAbortFIO(vy_fio_handle fio) {
 | 
				
			||||||
    if (fio == 0)
 | 
					    if (fio == 0)
 | 
				
			||||||
        return;
 | 
					        return;
 | 
				
			||||||
#ifdef __linux__
 | 
					#ifdef __linux__
 | 
				
			||||||
@ -346,7 +346,7 @@ void vyAbortFIO(vy_fio_handle fio) {
 | 
				
			|||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyIsFIOFinished(vy_fio_handle fio) {
 | 
					VY_DLLEXPORT bool vyIsFIOFinished(vy_fio_handle fio) {
 | 
				
			||||||
    if (fio == 0)
 | 
					    if (fio == 0)
 | 
				
			||||||
        return false;
 | 
					        return false;
 | 
				
			||||||
#ifdef __linux__
 | 
					#ifdef __linux__
 | 
				
			||||||
@ -363,7 +363,8 @@ bool vyIsFIOFinished(vy_fio_handle fio) {
 | 
				
			|||||||
    return result;
 | 
					    return result;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyRetrieveReadBuffer(vy_fio_handle fio, vy_file_buffer *buffer) {
 | 
					VY_DLLEXPORT bool vyRetrieveReadBuffer(vy_fio_handle fio,
 | 
				
			||||||
 | 
					                                       vy_file_buffer *buffer) {
 | 
				
			||||||
    if (fio == 0)
 | 
					    if (fio == 0)
 | 
				
			||||||
        return false;
 | 
					        return false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -394,7 +395,7 @@ bool vyRetrieveReadBuffer(vy_fio_handle fio, vy_file_buffer *buffer) {
 | 
				
			|||||||
    return is_finished;
 | 
					    return is_finished;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyFreeFileBuffer(vy_file_buffer buffer) {
 | 
					VY_DLLEXPORT void vyFreeFileBuffer(vy_file_buffer buffer) {
 | 
				
			||||||
    free(buffer.data);
 | 
					    free(buffer.data);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
							
								
								
									
										61
									
								
								src/runtime/fio.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										61
									
								
								src/runtime/fio.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,61 @@
 | 
				
			|||||||
 | 
					#ifndef VY_FIO_H
 | 
				
			||||||
 | 
					#define VY_FIO_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <stdbool.h>
 | 
				
			||||||
 | 
					#include <stddef.h>
 | 
				
			||||||
 | 
					#include <stdint.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					enum
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					    VY_FILE_BUFFER_FLAG_FILE_NOT_FOUND = 0x1,
 | 
				
			||||||
 | 
					    VY_FILE_BUFFER_FLAG_READ_FAILED    = 0x2,
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    void *data;
 | 
				
			||||||
 | 
					    size_t size;
 | 
				
			||||||
 | 
					    uint32_t flags;
 | 
				
			||||||
 | 
					} vy_file_buffer;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					inline bool vyWasFileBufferSuccessful(const vy_file_buffer *fb) {
 | 
				
			||||||
 | 
					    return fb->flags == 0;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* used to identify a file (XXH3 hash of the path) */
 | 
				
			||||||
 | 
					typedef uint64_t vy_file_id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef unsigned int vy_fio_handle;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    unsigned int queue_size;
 | 
				
			||||||
 | 
					    unsigned int max_file_count;
 | 
				
			||||||
 | 
					} vy_fio_config;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyInitFIO(const vy_fio_config *config);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyShutdownFIO(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_file_id vyGetFileId(const char *path);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_file_id vyGetFileIdFromSpan(vy_text_span path);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_file_id vyAddFile(const char *path);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_file_id vyAddFileFromSpan(vy_text_span path);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT const char *vyGetFilePath(vy_file_id fid);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_fio_handle vyEnqueueRead(vy_file_id fid);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyAbortFIO(vy_fio_handle fio);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyIsFIOFinished(vy_fio_handle fio);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyRetrieveReadBuffer(vy_fio_handle fio,
 | 
				
			||||||
 | 
					                                      vy_file_buffer *buffer);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyFreeFileBuffer(vy_file_buffer buffer);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
@ -1,8 +1,6 @@
 | 
				
			|||||||
#ifndef VY_GFX_H
 | 
					#ifndef VY_GFX_H
 | 
				
			||||||
#define VY_GFX_H
 | 
					#define VY_GFX_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include <stdint.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
/* graphics system. this is the interface of the rendering code.
 | 
					/* graphics system. this is the interface of the rendering code.
 | 
				
			||||||
 *
 | 
					 *
 | 
				
			||||||
 * we need (at least) three different renderers:
 | 
					 * we need (at least) three different renderers:
 | 
				
			||||||
@ -11,11 +9,17 @@
 | 
				
			|||||||
 * - object renderer (for static models)
 | 
					 * - object renderer (for static models)
 | 
				
			||||||
 */
 | 
					 */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <stdint.h>
 | 
				
			||||||
#include <stdbool.h>
 | 
					#include <stdbool.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyInitRenderer(void);
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyShutdownRenderer(void);
 | 
					/* In renderer_api.h -> Not necessary for almost all gfx usage */
 | 
				
			||||||
 | 
					typedef struct vy_renderer_init_info_s vy_renderer_init_info;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyInitGFX(vy_renderer_init_info *renderer_info);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyShutdownGFX(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* Generational indices for backend objects */
 | 
					/* Generational indices for backend objects */
 | 
				
			||||||
typedef struct {
 | 
					typedef struct {
 | 
				
			||||||
							
								
								
									
										75
									
								
								src/runtime/gfx_main.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										75
									
								
								src/runtime/gfx_main.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,75 @@
 | 
				
			|||||||
 | 
					#include <string.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define VY_DONT_DEFINE_RENDERER_GLOBAL
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "gfx.h"
 | 
				
			||||||
 | 
					#include "renderer_api.h"
 | 
				
			||||||
 | 
					#include "config.h"
 | 
				
			||||||
 | 
					#include "dynamic_libs.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Attributes are used to bind buffers (or textures) to symbolic values.
 | 
				
			||||||
 | 
					 * For example, an attribute might be bound to "CELL_GRID", which would be
 | 
				
			||||||
 | 
					 * replaced with the (at the time of the invoke) grid buffer of the current
 | 
				
			||||||
 | 
					 * world cell.
 | 
				
			||||||
 | 
					 */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					vy_renderer_api g_renderer;
 | 
				
			||||||
 | 
					static vy_dynlib _renderer_lib;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_CVAR_S(rt_Renderer,
 | 
				
			||||||
 | 
					          "Select the render backend. Available options: [vk], Default: vk",
 | 
				
			||||||
 | 
					          "vk");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern bool vyLoadShaders(const char **paths, vy_shader *shaders, unsigned int count);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static bool LoadRenderer(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					#define RETRIEVE_SYMBOL(name, type)                                            \
 | 
				
			||||||
 | 
					    g_renderer.name = (type *)vyGetSymbol(_renderer_lib, "vy" #name);          \
 | 
				
			||||||
 | 
					    if (!g_renderer.name) { \
 | 
				
			||||||
 | 
					        vyReportError(                                                         \
 | 
				
			||||||
 | 
					            "GFX",                                                             \
 | 
				
			||||||
 | 
					            "Unable to retrieve renderer function %s from backend %s",         \
 | 
				
			||||||
 | 
					            #name, rt_Renderer.s); \
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (strcmp(rt_Renderer.s, "vk") == 0) {
 | 
				
			||||||
 | 
					        _renderer_lib = vyOpenLib(VY_DLLNAME("vyvk"));
 | 
				
			||||||
 | 
					        if (!_renderer_lib) {
 | 
				
			||||||
 | 
					            vyReportError("GFX",
 | 
				
			||||||
 | 
					                          "Unable to load renderer backend: %s",
 | 
				
			||||||
 | 
					                          VY_DLLNAME("vyvk"));
 | 
				
			||||||
 | 
					            return false;
 | 
				
			||||||
 | 
					        }
 | 
				
			||||||
 | 
					        RETRIEVE_SYMBOL(Init, vy_init_renderer_fn);
 | 
				
			||||||
 | 
					        RETRIEVE_SYMBOL(Shutdown, vy_shutdown_renderer_fn);
 | 
				
			||||||
 | 
					        RETRIEVE_SYMBOL(CompileComputePipeline, vy_compile_compute_pipeline_fn);
 | 
				
			||||||
 | 
					        RETRIEVE_SYMBOL(CompileGraphicsPipeline,
 | 
				
			||||||
 | 
					                        vy_compile_graphics_pipeline_fn);
 | 
				
			||||||
 | 
					        return true;
 | 
				
			||||||
 | 
					    } else {
 | 
				
			||||||
 | 
					        vyReportError("GFX", "Unsupported renderer backend: (%s) %s", rt_Renderer.name, rt_Renderer.s);
 | 
				
			||||||
 | 
					        return false;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					#undef RETRIEVE_SYMBOL
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyInitGFX(vy_renderer_init_info *renderer_info) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (!LoadRenderer())
 | 
				
			||||||
 | 
					        return false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (g_renderer.Init(renderer_info) != 0)
 | 
				
			||||||
 | 
					        return false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    /* Init shader programs */
 | 
				
			||||||
 | 
					    const char *shader_files[] = {"shader/cell.shader"};
 | 
				
			||||||
 | 
					    vy_shader shaders[1];
 | 
				
			||||||
 | 
					    if (!vyLoadShaders(shader_files, shaders, 1))
 | 
				
			||||||
 | 
					        return false;
 | 
				
			||||||
 | 
					    return true;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyShutdownGFX(void) {
 | 
				
			||||||
 | 
					    g_renderer.Shutdown();
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@ -6,10 +6,10 @@
 | 
				
			|||||||
#include <stdlib.h>
 | 
					#include <stdlib.h>
 | 
				
			||||||
#include <string.h>
 | 
					#include <string.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime.h"
 | 
				
			||||||
#include "fio.h"
 | 
					#include "fio.h"
 | 
				
			||||||
#include "gfx.h"
 | 
					#include "gfx.h"
 | 
				
			||||||
#include "gfx_backend.h"
 | 
					#include "renderer_api.h"
 | 
				
			||||||
#include "voyage.h"
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
typedef enum {
 | 
					typedef enum {
 | 
				
			||||||
    VY_STMT_FORM_VALUE,
 | 
					    VY_STMT_FORM_VALUE,
 | 
				
			||||||
@ -289,9 +289,9 @@ static vy_fio_handle DispatchShaderRead(const char *shader,
 | 
				
			|||||||
    return DispatchFileRead(path->value);
 | 
					    return DispatchFileRead(path->value);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static vy_gfx_pipeline_id LinkProgram(vy_parse_state *state,
 | 
					static vy_gfx_pipeline_id CreatePipeline(vy_parse_state *state,
 | 
				
			||||||
                                      const char *file_path,
 | 
					                                         const char *file_path,
 | 
				
			||||||
                                      unsigned int root_list) {
 | 
					                                         unsigned int root_list) {
 | 
				
			||||||
    /* Process the data */
 | 
					    /* Process the data */
 | 
				
			||||||
    vy_fio_handle vertex_read =
 | 
					    vy_fio_handle vertex_read =
 | 
				
			||||||
        DispatchShaderRead("vertex", state, root_list, file_path);
 | 
					        DispatchShaderRead("vertex", state, root_list, file_path);
 | 
				
			||||||
@ -324,7 +324,7 @@ static vy_gfx_pipeline_id LinkProgram(vy_parse_state *state,
 | 
				
			|||||||
        vy_compute_pipeline_info info;
 | 
					        vy_compute_pipeline_info info;
 | 
				
			||||||
        info.compute_source         = compute_code.data;
 | 
					        info.compute_source         = compute_code.data;
 | 
				
			||||||
        info.compute_source_length  = compute_code.size;
 | 
					        info.compute_source_length  = compute_code.size;
 | 
				
			||||||
        vy_gfx_pipeline_id pipeline = vyCompileComputePipeline(&info);
 | 
					        vy_gfx_pipeline_id pipeline = g_renderer.CompileComputePipeline(&info);
 | 
				
			||||||
        vyFreeFileBuffer(compute_code);
 | 
					        vyFreeFileBuffer(compute_code);
 | 
				
			||||||
        return pipeline;
 | 
					        return pipeline;
 | 
				
			||||||
    } else if (vertex_read || fragment_read) {
 | 
					    } else if (vertex_read || fragment_read) {
 | 
				
			||||||
@ -386,7 +386,7 @@ static vy_gfx_pipeline_id LinkProgram(vy_parse_state *state,
 | 
				
			|||||||
            }
 | 
					            }
 | 
				
			||||||
        }
 | 
					        }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        vy_gfx_pipeline_id pipeline = vyCompileGraphicsPipeline(&info);
 | 
					        vy_gfx_pipeline_id pipeline = g_renderer.CompileGraphicsPipeline(&info);
 | 
				
			||||||
        vyFreeFileBuffer(vertex_code);
 | 
					        vyFreeFileBuffer(vertex_code);
 | 
				
			||||||
        vyFreeFileBuffer(fragment_code);
 | 
					        vyFreeFileBuffer(fragment_code);
 | 
				
			||||||
        return pipeline;
 | 
					        return pipeline;
 | 
				
			||||||
@ -515,7 +515,7 @@ ParseShaderFile(vy_file_id fid, vy_file_buffer fbuf, vy_shader *shader) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
    DbgPrintShaderFile(&state, root_list, 0);
 | 
					    DbgPrintShaderFile(&state, root_list, 0);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    shader->pipeline = LinkProgram(&state, file_path, root_list);
 | 
					    shader->pipeline = CreatePipeline(&state, file_path, root_list);
 | 
				
			||||||
    if (!VY_IS_GFX_ID_VALID(shader->pipeline)) {
 | 
					    if (!VY_IS_GFX_ID_VALID(shader->pipeline)) {
 | 
				
			||||||
        result = false;
 | 
					        result = false;
 | 
				
			||||||
        goto out;
 | 
					        goto out;
 | 
				
			||||||
							
								
								
									
										53
									
								
								src/runtime/renderer_api.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										53
									
								
								src/runtime/renderer_api.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,53 @@
 | 
				
			|||||||
 | 
					#ifndef VY_GFX_BACKEND_H
 | 
				
			||||||
 | 
					#define VY_GFX_BACKEND_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Backend functions and types. */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <stddef.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "gfx.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					struct HINSTANCE__;
 | 
				
			||||||
 | 
					struct HWND__;
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					struct vy_renderer_init_info_s {
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					    struct HINSTANCE__ *hInstance;
 | 
				
			||||||
 | 
					    struct HWND__ *hWnd;
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    const char *compute_source;
 | 
				
			||||||
 | 
					    size_t compute_source_length;
 | 
				
			||||||
 | 
					} vy_compute_pipeline_info;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    const char *vertex_source;
 | 
				
			||||||
 | 
					    size_t vertex_source_length;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    const char *fragment_source;
 | 
				
			||||||
 | 
					    size_t fragment_source_length;
 | 
				
			||||||
 | 
					} vy_graphics_pipeline_info;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef int vy_init_renderer_fn(const vy_renderer_init_info *info);
 | 
				
			||||||
 | 
					typedef void vy_shutdown_renderer_fn(void);
 | 
				
			||||||
 | 
					typedef vy_gfx_pipeline_id
 | 
				
			||||||
 | 
					vy_compile_compute_pipeline_fn(const vy_compute_pipeline_info *info);
 | 
				
			||||||
 | 
					typedef vy_gfx_pipeline_id
 | 
				
			||||||
 | 
					vy_compile_graphics_pipeline_fn(const vy_graphics_pipeline_info *info);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct {
 | 
				
			||||||
 | 
					    vy_init_renderer_fn *Init;
 | 
				
			||||||
 | 
					    vy_shutdown_renderer_fn *Shutdown;
 | 
				
			||||||
 | 
					    vy_compile_compute_pipeline_fn *CompileComputePipeline;
 | 
				
			||||||
 | 
					    vy_compile_graphics_pipeline_fn *CompileGraphicsPipeline;
 | 
				
			||||||
 | 
					} vy_renderer_api;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifndef VY_DONT_DEFINE_RENDERER_GLOBAL
 | 
				
			||||||
 | 
					extern vy_renderer_api g_renderer;
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
@ -5,6 +5,12 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
#include <stddef.h>
 | 
					#include <stddef.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#ifdef _WIN32
 | 
				
			||||||
 | 
					        #define VY_DLLEXPORT __declspec(dllexport)
 | 
				
			||||||
 | 
					#else
 | 
				
			||||||
 | 
					        #define VY_DLLEXPORT
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define VY_UNUSED(x) ((void)sizeof((x)))
 | 
					#define VY_UNUSED(x) ((void)sizeof((x)))
 | 
				
			||||||
#define VY_ARRAY_COUNT(x) (sizeof((x)) / sizeof((x)[0]))
 | 
					#define VY_ARRAY_COUNT(x) (sizeof((x)) / sizeof((x)[0]))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@ -13,8 +19,8 @@ typedef struct {
 | 
				
			|||||||
    unsigned int length;
 | 
					    unsigned int length;
 | 
				
			||||||
} vy_text_span;
 | 
					} vy_text_span;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyReportError(const char *subsystem, const char *fmt, ...);
 | 
					VY_DLLEXPORT void vyReportError(const char *subsystem, const char *fmt, ...);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyLog(const char *subsystem, const char *fmt, ...);
 | 
					VY_DLLEXPORT void vyLog(const char *subsystem, const char *fmt, ...);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
							
								
								
									
										14
									
								
								src/runtime/runtime_cvars.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										14
									
								
								src/runtime/runtime_cvars.c
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,14 @@
 | 
				
			|||||||
 | 
					#include "config.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern vy_cvar rt_Renderer;
 | 
				
			||||||
 | 
					extern vy_cvar rt_Fullscreen;
 | 
				
			||||||
 | 
					extern vy_cvar rt_WindowWidth;
 | 
				
			||||||
 | 
					extern vy_cvar rt_WindowHeight;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void __RegisterRuntimeCVars(void)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					    vyRegisterCVAR(&rt_Renderer);
 | 
				
			||||||
 | 
					    vyRegisterCVAR(&rt_Fullscreen);
 | 
				
			||||||
 | 
					    vyRegisterCVAR(&rt_WindowWidth);
 | 
				
			||||||
 | 
					    vyRegisterCVAR(&rt_WindowHeight);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@ -1,5 +1,5 @@
 | 
				
			|||||||
#include "threading.h"
 | 
					#include "threading.h"
 | 
				
			||||||
#include "voyage.h"
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#ifdef _WIN32
 | 
					#ifdef _WIN32
 | 
				
			||||||
#define WIN32_LEAN_AND_MEAN
 | 
					#define WIN32_LEAN_AND_MEAN
 | 
				
			||||||
@ -15,7 +15,7 @@ static vy_mutex _mutex[MAX_MUTEX];
 | 
				
			|||||||
static ptrdiff_t _first_reusable = MAX_MUTEX;
 | 
					static ptrdiff_t _first_reusable = MAX_MUTEX;
 | 
				
			||||||
static ptrdiff_t _next       = 0;
 | 
					static ptrdiff_t _next       = 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_mutex *vyCreateMutex(void) {
 | 
					VY_DLLEXPORT vy_mutex *vyCreateMutex(void) {
 | 
				
			||||||
    if (_first_reusable < MAX_MUTEX) {
 | 
					    if (_first_reusable < MAX_MUTEX) {
 | 
				
			||||||
        vy_mutex *mtx   = &_mutex[_first_reusable];
 | 
					        vy_mutex *mtx   = &_mutex[_first_reusable];
 | 
				
			||||||
        _first_reusable = mtx->next_reusable;
 | 
					        _first_reusable = mtx->next_reusable;
 | 
				
			||||||
@ -35,18 +35,18 @@ vy_mutex *vyCreateMutex(void) {
 | 
				
			|||||||
    return NULL;
 | 
					    return NULL;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyDestroyMutex(vy_mutex *mutex) {
 | 
					VY_DLLEXPORT void vyDestroyMutex(vy_mutex *mutex) {
 | 
				
			||||||
    ptrdiff_t index      = mutex - &_mutex[0];
 | 
					    ptrdiff_t index      = mutex - &_mutex[0];
 | 
				
			||||||
    mutex->next_reusable = _first_reusable;
 | 
					    mutex->next_reusable = _first_reusable;
 | 
				
			||||||
    _first_reusable      = index;
 | 
					    _first_reusable      = index;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyLockMutex(vy_mutex *mutex) {
 | 
					VY_DLLEXPORT bool vyLockMutex(vy_mutex *mutex) {
 | 
				
			||||||
    return WaitForSingleObject(mutex->handle, INFINITE) == WAIT_OBJECT_0;
 | 
					    return WaitForSingleObject(mutex->handle, INFINITE) == WAIT_OBJECT_0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyUnlockMutex(vy_mutex *mutex) {
 | 
					VY_DLLEXPORT bool vyUnlockMutex(vy_mutex *mutex) {
 | 
				
			||||||
    return ReleaseMutex(mutex) != 0;
 | 
					    return ReleaseMutex(mutex->handle) != 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#elif defined(__linux__)
 | 
					#elif defined(__linux__)
 | 
				
			||||||
@ -62,7 +62,7 @@ static vy_mutex _mutex[MAX_MUTEX];
 | 
				
			|||||||
static ptrdiff_t _first_reusable = MAX_MUTEX;
 | 
					static ptrdiff_t _first_reusable = MAX_MUTEX;
 | 
				
			||||||
static ptrdiff_t _next           = 0;
 | 
					static ptrdiff_t _next           = 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
vy_mutex *vyCreateMutex(void) {
 | 
					VY_DLLEXPORT vy_mutex *vyCreateMutex(void) {
 | 
				
			||||||
    if (_first_reusable < MAX_MUTEX) {
 | 
					    if (_first_reusable < MAX_MUTEX) {
 | 
				
			||||||
        vy_mutex *mtx   = &_mutex[_first_reusable];
 | 
					        vy_mutex *mtx   = &_mutex[_first_reusable];
 | 
				
			||||||
        _first_reusable = mtx->next_reusable;
 | 
					        _first_reusable = mtx->next_reusable;
 | 
				
			||||||
@ -81,17 +81,17 @@ vy_mutex *vyCreateMutex(void) {
 | 
				
			|||||||
    return NULL;
 | 
					    return NULL;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void vyDestroyMutex(vy_mutex *mutex) {
 | 
					VY_DLLEXPORT void vyDestroyMutex(vy_mutex *mutex) {
 | 
				
			||||||
    ptrdiff_t index      = mutex - &_mutex[0];
 | 
					    ptrdiff_t index      = mutex - &_mutex[0];
 | 
				
			||||||
    mutex->next_reusable = _first_reusable;
 | 
					    mutex->next_reusable = _first_reusable;
 | 
				
			||||||
    _first_reusable      = index;
 | 
					    _first_reusable      = index;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyLockMutex(vy_mutex *mutex) {
 | 
					VY_DLLEXPORT bool vyLockMutex(vy_mutex *mutex) {
 | 
				
			||||||
    return pthread_mutex_lock(&mutex->handle) == 0;
 | 
					    return pthread_mutex_lock(&mutex->handle) == 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool vyUnlockMutex(vy_mutex *mutex) {
 | 
					VY_DLLEXPORT bool vyUnlockMutex(vy_mutex *mutex) {
 | 
				
			||||||
    return pthread_mutex_unlock(&mutex->handle) == 0;
 | 
					    return pthread_mutex_unlock(&mutex->handle) == 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
							
								
								
									
										20
									
								
								src/runtime/threading.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										20
									
								
								src/runtime/threading.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,20 @@
 | 
				
			|||||||
 | 
					#ifndef VY_THREADING_H
 | 
				
			||||||
 | 
					#define VY_THREADING_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* platform independent threading */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <stdbool.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "runtime.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					typedef struct vy_mutex_s vy_mutex;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT vy_mutex *vyCreateMutex(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT void vyDestroyMutex(vy_mutex *mutex);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyLockMutex(vy_mutex *mutex);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					VY_DLLEXPORT bool vyUnlockMutex(vy_mutex *mutex);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
							
								
								
									
										115
									
								
								src/voyage.c
									
									
									
									
									
								
							
							
						
						
									
										115
									
								
								src/voyage.c
									
									
									
									
									
								
							@ -1,115 +0,0 @@
 | 
				
			|||||||
#include <glad/glad.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include <GLFW/glfw3.h>
 | 
					 | 
				
			||||||
#include <assert.h>
 | 
					 | 
				
			||||||
#include <stdio.h>
 | 
					 | 
				
			||||||
#include <string.h>
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#include "fio.h"
 | 
					 | 
				
			||||||
#include "gfx.h"
 | 
					 | 
				
			||||||
#include "threading.h"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
static void glfw_error_cb(int err, const char *description) {
 | 
					 | 
				
			||||||
    fprintf(stderr, "[GLFW] %u: %s\n", err, description);
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
static void make_window_windowed_fullscreen(GLFWwindow *window,
 | 
					 | 
				
			||||||
                                            GLFWmonitor *monitor) {
 | 
					 | 
				
			||||||
    const GLFWvidmode *mode = glfwGetVideoMode(monitor);
 | 
					 | 
				
			||||||
    glfwSetWindowMonitor(window,
 | 
					 | 
				
			||||||
                         monitor,
 | 
					 | 
				
			||||||
                         0,
 | 
					 | 
				
			||||||
                         0,
 | 
					 | 
				
			||||||
                         mode->width,
 | 
					 | 
				
			||||||
                         mode->height,
 | 
					 | 
				
			||||||
                         mode->refreshRate);
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
static void make_window_windowed(GLFWwindow *window, int w, int h) {
 | 
					 | 
				
			||||||
    glfwSetWindowMonitor(window, NULL, 0, 0, w, h, GLFW_DONT_CARE);
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
typedef struct {
 | 
					 | 
				
			||||||
    int f1;
 | 
					 | 
				
			||||||
    int esc;
 | 
					 | 
				
			||||||
} key_states;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
int main(int argc, char **argv) {
 | 
					 | 
				
			||||||
    glfwSetErrorCallback(glfw_error_cb);
 | 
					 | 
				
			||||||
    if (!glfwInit()) {
 | 
					 | 
				
			||||||
        return 1;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    printf("[GFLW] Version: %s\n", glfwGetVersionString());
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    /* Create a windowed full screen window */
 | 
					 | 
				
			||||||
    glfwWindowHint(GLFW_CLIENT_API, GLFW_OPENGL_API);
 | 
					 | 
				
			||||||
    glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
 | 
					 | 
				
			||||||
    glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4);
 | 
					 | 
				
			||||||
    glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 5);
 | 
					 | 
				
			||||||
    GLFWwindow *window = glfwCreateWindow(640, 480, "Voyage", NULL, NULL);
 | 
					 | 
				
			||||||
    if (!window) {
 | 
					 | 
				
			||||||
        fprintf(stderr, "[GFX] Window creation failed.\n");
 | 
					 | 
				
			||||||
        return 1;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    glfwMakeContextCurrent(window);
 | 
					 | 
				
			||||||
    glfwSwapInterval(1);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    if (!gladLoadGL()) {
 | 
					 | 
				
			||||||
        fprintf(stderr, "[GFX] OpenGL load failed.\n");
 | 
					 | 
				
			||||||
        return 1;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    vy_fio_config fio_config = {0};
 | 
					 | 
				
			||||||
    if (!vyInitFIO(&fio_config)) {
 | 
					 | 
				
			||||||
        fprintf(stderr, "[FIO] Init failed.\n");
 | 
					 | 
				
			||||||
        return 1;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    if (!vyInitRenderer()) {
 | 
					 | 
				
			||||||
        fprintf(stderr, "[GFX] Init failed.\n");
 | 
					 | 
				
			||||||
        return 1;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
    printf("GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS: %u\n",
 | 
					 | 
				
			||||||
           GL_MAX_SHADER_STORAGE_BUFFER_BINDINGS);
 | 
					 | 
				
			||||||
    printf("GL_MAX_UNIFORM_BUFFER_BINDINGS: %u\n",
 | 
					 | 
				
			||||||
           GL_MAX_UNIFORM_BUFFER_BINDINGS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    key_states prev_keys = {0};
 | 
					 | 
				
			||||||
    int window_state     = 0;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    while (!glfwWindowShouldClose(window)) {
 | 
					 | 
				
			||||||
        /* Gather input */
 | 
					 | 
				
			||||||
        key_states keys;
 | 
					 | 
				
			||||||
        keys.f1  = glfwGetKey(window, GLFW_KEY_F1);
 | 
					 | 
				
			||||||
        keys.esc = glfwGetKey(window, GLFW_KEY_ESCAPE);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (keys.f1 && !prev_keys.f1) {
 | 
					 | 
				
			||||||
            if (window_state)
 | 
					 | 
				
			||||||
                make_window_windowed(window, 640, 480);
 | 
					 | 
				
			||||||
            else
 | 
					 | 
				
			||||||
                make_window_windowed_fullscreen(window,
 | 
					 | 
				
			||||||
                                                glfwGetPrimaryMonitor());
 | 
					 | 
				
			||||||
            window_state = !window_state;
 | 
					 | 
				
			||||||
        }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        if (keys.esc)
 | 
					 | 
				
			||||||
            glfwSetWindowShouldClose(window, GLFW_TRUE);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        int fbw, fbh;
 | 
					 | 
				
			||||||
        glfwGetFramebufferSize(window, &fbw, &fbh);
 | 
					 | 
				
			||||||
        glViewport(0, 0, fbw, fbh);
 | 
					 | 
				
			||||||
        glClearColor(0, 0, 0, 0);
 | 
					 | 
				
			||||||
        glClear(GL_COLOR_BUFFER_BIT);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        glfwSwapBuffers(window);
 | 
					 | 
				
			||||||
        glfwPollEvents();
 | 
					 | 
				
			||||||
        prev_keys = keys;
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    vyShutdownRenderer();
 | 
					 | 
				
			||||||
    vyShutdownFIO();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    glfwDestroyWindow(window);
 | 
					 | 
				
			||||||
    glfwTerminate();
 | 
					 | 
				
			||||||
    return 0;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
		Loading…
	
		Reference in New Issue
	
	Block a user