Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
V
virtual_game_machine
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Package registry
Model registry
Operate
Environments
Terraform modules
Monitor
Incidents
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
adrian.spycher
virtual_game_machine
Commits
f7fd33e6
Commit
f7fd33e6
authored
6 months ago
by
adrian.spycher
Browse files
Options
Downloads
Patches
Plain Diff
feat: add gfx wrapper
parent
b472c651
No related branches found
No related tags found
No related merge requests found
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
vmm/Makefile
+2
-1
2 additions, 1 deletion
vmm/Makefile
vmm/gfx.c
+202
-0
202 additions, 0 deletions
vmm/gfx.c
vmm/gfx.h
+54
-0
54 additions, 0 deletions
vmm/gfx.h
with
258 additions
and
1 deletion
vmm/Makefile
+
2
−
1
View file @
f7fd33e6
CC
=
gcc
-std
=
gnu17
-Wall
-Wextra
-MMD
-Ishared
-I
../..
-I
..
CC
=
gcc
-std
=
gnu17
-Wall
-Wextra
-MMD
-Ishared
-I
../..
-I
..
LIBS
=
-lSDL2
-lSDL2_image
C_SRCS
=
$(
shell find
.
-name
"*.c"
)
C_SRCS
=
$(
shell find
.
-name
"*.c"
)
C_OBJS
=
$(
C_SRCS:.c
=
.o
)
C_OBJS
=
$(
C_SRCS:.c
=
.o
)
C_DEPS
=
$(
C_OBJS:%.o
=
%.d
)
C_DEPS
=
$(
C_OBJS:%.o
=
%.d
)
$(OUT)
:
$(C_OBJS)
$(OUT)
:
$(C_OBJS)
$(
CC
)
$^
-o
$@
$(
CC
)
$^
-o
$@
$(
LIBS
)
%.o
:
%.c
%.o
:
%.c
$(
CC
)
-c
$<
-o
$@
$(
CC
)
-c
$<
-o
$@
...
...
This diff is collapsed.
Click to expand it.
vmm/gfx.c
0 → 100644
+
202
−
0
View file @
f7fd33e6
/// @file gfx.c
/// @author Florent Gluck
/// @date 2016-2024
/// Helper routines for super simple graphics rendering.
/// Requires the SDL2 library.
#include
"gfx.h"
#include
<signal.h>
/// Create a fullscreen graphic window.
/// @param title window title.
/// @param width window's width in pixels.
/// @param height window's height in pixels.
/// @return a pointer to the graphic context or NULL if it failed.
gfx_context_t
*
gfx_create
(
char
*
title
,
int
width
,
int
height
)
{
if
(
SDL_Init
(
SDL_INIT_VIDEO
)
!=
0
)
{
fprintf
(
stderr
,
"%s"
,
SDL_GetError
());
goto
error
;
}
// Restore SIGINT's default behavior so that we can use CTRL-C to stop the program
struct
sigaction
act
;
memset
(
&
act
,
0
,
sizeof
(
act
));
act
.
sa_handler
=
SIG_DFL
;
if
(
sigaction
(
SIGINT
,
&
act
,
NULL
)
<
0
)
{
perror
(
"sigaction"
);
exit
(
1
);
}
// These a just for reference:
// SDL_SetHint(SDL_HINT_NO_SIGNAL_HANDLERS, "1");
// SDL_SetHint(SDL_HINT_RENDER_DRIVER, "software"); // opengl, opengles2, software
// SDL_SetHint(SDL_HINT_RENDER_OPENGL_SHADERS, "0");
// SDL_SetHint(SDL_HINT_RENDER_VSYNC, "0");
// SDL_SetHint(SDL_HINT_VIDEO_X11_NET_WM_PING, "0");
// SDL_SetHint(SDL_HINT_VIDEO_X11_XVIDMODE, "0");
SDL_Window
*
window
=
SDL_CreateWindow
(
title
,
SDL_WINDOWPOS_CENTERED
,
SDL_WINDOWPOS_CENTERED
,
width
,
height
,
SDL_WINDOW_OPENGL
|
SDL_WINDOW_RESIZABLE
);
SDL_Renderer
*
renderer
=
SDL_CreateRenderer
(
window
,
-
1
,
SDL_RENDERER_ACCELERATED
);
SDL_Texture
*
background_texture
=
SDL_CreateTexture
(
renderer
,
SDL_PIXELFORMAT_ARGB8888
,
SDL_TEXTUREACCESS_STREAMING
,
width
,
height
);
gfx_context_t
*
ctxt
=
malloc
(
sizeof
(
gfx_context_t
));
// Retrieve the background texture's pitch
uint8_t
*
unused
;
SDL_LockTexture
(
background_texture
,
NULL
,
(
void
**
)
&
unused
,
&
ctxt
->
pitch
);
SDL_UnlockTexture
(
background_texture
);
pixel_t
*
background
=
malloc
(
ctxt
->
pitch
*
height
);
if
(
!
window
||
!
renderer
||
!
background_texture
||
!
background
||
!
ctxt
)
goto
error
;
ctxt
->
renderer
=
renderer
;
ctxt
->
background_texture
=
background_texture
;
ctxt
->
window
=
window
;
ctxt
->
width
=
width
;
ctxt
->
height
=
height
;
ctxt
->
background
=
background
;
SDL_ShowCursor
(
SDL_DISABLE
);
gfx_background_clear
(
ctxt
,
GFX_COL_BLACK
);
return
ctxt
;
error:
return
NULL
;
}
/// Draw a pixel in the background buffer.
/// @param ctxt graphic context.
/// @param x x coordinate of the pixel.
/// @param y y coordinate of the pixel.
/// @param color pixel color.
void
gfx_background_putpixel
(
gfx_context_t
*
ctxt
,
int
x
,
int
y
,
pixel_t
color
)
{
if
(
x
<
ctxt
->
width
&&
y
<
ctxt
->
height
)
{
ctxt
->
background
[
ctxt
->
pitch
/
sizeof
(
pixel_t
)
*
y
+
x
]
=
color
;
}
}
/// Clear the background buffer.
/// @param ctxt graphic context.
/// @param color fill color.
void
gfx_background_clear
(
gfx_context_t
*
ctxt
,
pixel_t
color
)
{
for
(
int
j
=
0
;
j
<
ctxt
->
height
;
j
++
)
{
for
(
int
i
=
0
;
i
<
ctxt
->
width
;
i
++
)
{
ctxt
->
background
[
ctxt
->
pitch
/
sizeof
(
pixel_t
)
*
j
+
i
]
=
color
;
}
}
}
/// Copy the background buffer to the display buffer.
/// @param ctxt graphic context.
void
gfx_background_update
(
gfx_context_t
*
ctxt
)
{
SDL_UpdateTexture
(
ctxt
->
background_texture
,
NULL
,
ctxt
->
background
,
ctxt
->
width
*
sizeof
(
pixel_t
));
SDL_RenderCopy
(
ctxt
->
renderer
,
ctxt
->
background_texture
,
NULL
,
NULL
);
}
/// Show the display buffer.
/// @param ctxt graphic context.
void
gfx_present
(
gfx_context_t
*
ctxt
)
{
SDL_RenderPresent
(
ctxt
->
renderer
);
}
/// Destroy a graphic window.
/// @param ctxt graphic context.
void
gfx_destroy
(
gfx_context_t
*
ctxt
)
{
SDL_ShowCursor
(
SDL_ENABLE
);
SDL_DestroyTexture
(
ctxt
->
background_texture
);
SDL_DestroyRenderer
(
ctxt
->
renderer
);
SDL_DestroyWindow
(
ctxt
->
window
);
free
(
ctxt
->
background
);
ctxt
->
background_texture
=
NULL
;
ctxt
->
renderer
=
NULL
;
ctxt
->
window
=
NULL
;
ctxt
->
background
=
NULL
;
SDL_Quit
();
free
(
ctxt
);
}
/// If a key was pressed, returns its key code.
/// IMPORTANT: This is a non-blocking call!
/// List of key codes: https://wiki.libsdl.org/SDL_Keycode
/// @return the key that was pressed or 0 if none was pressed.
SDL_Keycode
gfx_keypressed
()
{
SDL_Event
event
;
if
(
SDL_PollEvent
(
&
event
))
{
if
(
event
.
type
==
SDL_KEYDOWN
)
return
event
.
key
.
keysym
.
sym
;
}
return
0
;
}
/// Load a sprite from an image file (png, jpg, etc.).
/// @param ctxt graphic context.
/// @param filename path to the file to load.
/// @return a pointer to the sprite or NULL in case of failure.
/// When not needed anymore, deallocate it with gfx_sprite_destroy.
SDL_Texture
*
gfx_sprite_load
(
gfx_context_t
*
ctxt
,
char
*
filename
)
{
SDL_Surface
*
sprite_surface
=
IMG_Load
(
filename
);
// Failed loading sprite.
if
(
!
sprite_surface
)
{
return
NULL
;
}
SDL_Texture
*
sprite_texture
=
SDL_CreateTextureFromSurface
(
ctxt
->
renderer
,
sprite_surface
);
if
(
!
sprite_texture
)
{
return
NULL
;
}
SDL_FreeSurface
(
sprite_surface
);
// Only the texture is needed
return
sprite_texture
;
}
/// Create a sprite from in-memory RGBA8888 pixels.
/// @param ctxt graphic context.
/// @param pixels array of pixels composing the sprite.
/// @param width sprite's width in pixels.
/// @param height sprite's height in pixels.
/// @return a pointer to the sprite or NULL in case of failure.
/// When not needed anymore, deallocate it with gfx_sprite_destroy.
SDL_Texture
*
gfx_sprite_create
(
gfx_context_t
*
ctxt
,
uint8_t
*
pixels
,
int
width
,
int
height
)
{
SDL_Texture
*
tex
=
SDL_CreateTexture
(
ctxt
->
renderer
,
SDL_PIXELFORMAT_ABGR8888
,
SDL_TEXTUREACCESS_STREAMING
,
width
,
height
);
if
(
!
tex
)
{
return
NULL
;
}
// Force renderer to use alpha blending when rendering the sprite.
SDL_SetTextureBlendMode
(
tex
,
SDL_BLENDMODE_BLEND
);
pixel_t
*
dst_pixels
;
pixel_t
*
src_pixels
=
(
pixel_t
*
)
pixels
;
int
pitch
;
if
(
SDL_LockTexture
(
tex
,
NULL
,
(
void
**
)
&
dst_pixels
,
&
pitch
)
!=
0
)
{
SDL_DestroyTexture
(
tex
);
return
NULL
;
}
for
(
int
j
=
0
;
j
<
height
;
j
++
)
{
for
(
int
i
=
0
;
i
<
width
;
i
++
)
{
dst_pixels
[
pitch
/
sizeof
(
pixel_t
)
*
j
+
i
]
=
*
src_pixels
;
src_pixels
++
;
}
}
SDL_UnlockTexture
(
tex
);
return
tex
;
}
/// Destroy a sprite that was loaded/created with gfx_sprite_load/gfx_sprite_create.
/// @param ctxt graphic context.
/// @param sprite the sprite (texture) to destroy.
void
gfx_sprite_destroy
(
SDL_Texture
*
sprite
)
{
SDL_DestroyTexture
(
sprite
);
}
/// Render a sprite at the specified position.
/// @param context graphic context.
/// @param sprite the sprite (texture) to render.
/// @param x sprite's x coordinate.
/// @param y sprite's y coordinate.
/// @param sprite_width sprite's display width in pixels.
/// @param sprite_height sprite's display height in pixels.
void
gfx_sprite_render
(
gfx_context_t
*
ctxt
,
SDL_Texture
*
sprite
,
int
x
,
int
y
,
int
sprite_width
,
int
sprite_height
)
{
SDL_Rect
dst_rect
=
{
x
,
y
,
sprite_width
,
sprite_height
};
SDL_RenderCopy
(
ctxt
->
renderer
,
sprite
,
NULL
,
&
dst_rect
);
}
This diff is collapsed.
Click to expand it.
vmm/gfx.h
0 → 100644
+
54
−
0
View file @
f7fd33e6
#ifndef _GFX_H_
#define _GFX_H_
#include
<stdint.h>
#include
<stdbool.h>
#include
<SDL2/SDL.h>
#include
<SDL2/SDL_image.h>
#define GFX_RGB(r,g,b) ((pixel_t){b,g,r,0})
#define GFX_COL_BLACK GFX_RGB(0,0,0)
#define GFX_COL_RED GFX_RGB(0,0,255)
#define GFX_COL_GREEN GFX_RGB(0,255,0)
#define GFX_COL_BLUE GFX_RGB(255,0,0)
#define GFX_COL_CYAN GFX_RGB(255,255,0)
#define GFX_COL_PURPLE GFX_RGB(255,0,255)
#define GFX_COL_YELLOW GFX_RGB(0,255,255)
#define GFX_COL_WHITE GFX_RGB(255,255,255)
// Structure of a pixel: 32-bits (ARGB)
typedef
struct
__attribute__
((
__packed__
))
{
uint8_t
b
;
uint8_t
g
;
uint8_t
r
;
uint8_t
a
;
}
pixel_t
;
typedef
struct
{
SDL_Window
*
window
;
SDL_Renderer
*
renderer
;
SDL_Texture
*
background_texture
;
pixel_t
*
background
;
int
pitch
;
int
width
;
int
height
;
}
gfx_context_t
;
gfx_context_t
*
gfx_create
(
char
*
text
,
int
width
,
int
height
);
void
gfx_destroy
(
gfx_context_t
*
ctxt
);
void
gfx_background_putpixel
(
gfx_context_t
*
ctxt
,
int
x
,
int
y
,
pixel_t
color
);
void
gfx_background_clear
(
gfx_context_t
*
ctxt
,
pixel_t
color
);
void
gfx_background_update
(
gfx_context_t
*
ctxt
);
SDL_Texture
*
gfx_sprite_load
(
gfx_context_t
*
ctxt
,
char
*
filename
);
SDL_Texture
*
gfx_sprite_create
(
gfx_context_t
*
ctxt
,
uint8_t
*
pixels
,
int
width
,
int
height
);
void
gfx_sprite_destroy
(
SDL_Texture
*
sprite
);
void
gfx_sprite_render
(
gfx_context_t
*
ctxt
,
SDL_Texture
*
sprite
,
int
x
,
int
y
,
int
sprite_width
,
int
sprite_height
);
void
gfx_present
(
gfx_context_t
*
ctxt
);
SDL_Keycode
gfx_keypressed
();
#endif
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment