diff options
-rw-r--r-- | README.md | 4 | ||||
m--------- | depends/mgl | 0 | ||||
-rw-r--r-- | include/mglpp/graphics/Font.hpp | 16 | ||||
-rw-r--r-- | include/mglpp/graphics/Texture.hpp | 9 | ||||
-rw-r--r-- | include/mglpp/system/MemoryMappedFile.hpp | 30 | ||||
-rw-r--r-- | include/mglpp/system/Utf8.hpp | 11 | ||||
-rw-r--r-- | include/mglpp/window/Clipboard.hpp | 2 | ||||
-rw-r--r-- | include/mglpp/window/Event.hpp | 22 | ||||
-rw-r--r-- | include/mglpp/window/Keyboard.hpp | 5 | ||||
-rw-r--r-- | include/mglpp/window/Mouse.hpp | 5 | ||||
-rw-r--r-- | include/mglpp/window/Window.hpp | 28 | ||||
-rw-r--r-- | src/graphics/Font.cpp | 18 | ||||
-rw-r--r-- | src/graphics/Shader.cpp | 4 | ||||
-rw-r--r-- | src/graphics/Sprite.cpp | 9 | ||||
-rw-r--r-- | src/graphics/Text.cpp | 4 | ||||
-rw-r--r-- | src/graphics/Texture.cpp | 28 | ||||
-rw-r--r-- | src/system/MemoryMappedFile.cpp | 36 | ||||
-rw-r--r-- | src/system/Utf8.cpp | 11 | ||||
-rw-r--r-- | src/window/Clipboard.cpp | 15 | ||||
-rw-r--r-- | src/window/Window.cpp | 69 | ||||
-rw-r--r-- | tests/main.cpp | 15 |
21 files changed, 244 insertions, 97 deletions
@@ -4,4 +4,6 @@ C++ wrapper for [mgl](https://git.dec05eba.com/mgl/about/) ## Build `xlib` ## Runtime -`libglvnd (libGL.so)`
\ No newline at end of file +`libglvnd (libGL.so)` +# Notes +Every window _get_ function is cached from the last event poll, no calls to x11 is made. diff --git a/depends/mgl b/depends/mgl -Subproject 16b0ce3748f1b3ea788bbaf4caaeb342a8f58d6 +Subproject eba962c3e353b3fd3f11e30a7d6f48585e3a153 diff --git a/include/mglpp/graphics/Font.hpp b/include/mglpp/graphics/Font.hpp index b032e13..440dabe 100644 --- a/include/mglpp/graphics/Font.hpp +++ b/include/mglpp/graphics/Font.hpp @@ -9,13 +9,14 @@ extern "C" { namespace mgl { class Texture; + class MemoryMappedFile; struct FontGlyph { - vec2f position; - vec2f size; - vec2f texture_position; - vec2f texture_size; - float advance = 0.0f; + vec2i position; + vec2i size; + vec2i texture_position; /* In pixel space */ + vec2i texture_size; /* In pixel space */ + int advance = 0; }; class Font { @@ -23,10 +24,11 @@ namespace mgl { Font(); ~Font(); - bool load_from_file(const char *filepath, unsigned int character_size); + bool load_from_file(const MemoryMappedFile &mapped_file, unsigned int character_size); unsigned int get_character_size() const; // Returns 0 sized glyph if the font doesn't have the codepoint - FontGlyph get_glyph(uint32_t codepoint) const; + FontGlyph get_glyph(uint32_t codepoint); + int get_kerning(uint32_t prev_codepoint, uint32_t codepoint); Texture get_texture() const; mgl_font* internal_font(); diff --git a/include/mglpp/graphics/Texture.hpp b/include/mglpp/graphics/Texture.hpp index 9559829..633d2cd 100644 --- a/include/mglpp/graphics/Texture.hpp +++ b/include/mglpp/graphics/Texture.hpp @@ -11,13 +11,18 @@ namespace mgl { class Image; class Texture { public: + struct LoadOptions { + bool compressed; + bool pixel_coordinates; + }; + Texture(); ~Texture(); static Texture reference(mgl_texture ref); - bool load_from_file(const char *filepath); - bool load_from_image(Image &image); + bool load_from_file(const char *filepath, const LoadOptions load_options = {false, false}); + bool load_from_image(Image &image, const LoadOptions load_options = {false, false}); vec2i get_size() const; bool is_valid() const; diff --git a/include/mglpp/system/MemoryMappedFile.hpp b/include/mglpp/system/MemoryMappedFile.hpp new file mode 100644 index 0000000..508518a --- /dev/null +++ b/include/mglpp/system/MemoryMappedFile.hpp @@ -0,0 +1,30 @@ +#ifndef MGLPP_MEMORY_MAPPED_FILE_HPP +#define MGLPP_MEMORY_MAPPED_FILE_HPP + +extern "C" { +#include <mgl/system/fileutils.h> +} + +namespace mgl { + class MemoryMappedFile { + public: + struct LoadOptions { + bool readable; + bool writable; + }; + + MemoryMappedFile(); + ~MemoryMappedFile(); + + bool load(const char *filepath, LoadOptions load_options = { true, true }); + + void* data(); + size_t size(); + + const mgl_memory_mapped_file* internal_mapped_file() const; + private: + mgl_memory_mapped_file memory_mapped_file; + }; +} + +#endif /* MGLPP_MEMORY_MAPPED_FILE_HPP */ diff --git a/include/mglpp/system/Utf8.hpp b/include/mglpp/system/Utf8.hpp new file mode 100644 index 0000000..4f6a39a --- /dev/null +++ b/include/mglpp/system/Utf8.hpp @@ -0,0 +1,11 @@ +#ifndef MGLPP_UTF8_HPP +#define MGLPP_UTF8_HPP + +#include <stddef.h> +#include <stdint.h> + +namespace mgl { + bool utf8_decode(const unsigned char *str, size_t size, uint32_t *decoded_codepoint, size_t *codepoint_length); +} + +#endif /* MGLPP_UTF8_HPP */ diff --git a/include/mglpp/window/Clipboard.hpp b/include/mglpp/window/Clipboard.hpp index 7d5c9d4..caec403 100644 --- a/include/mglpp/window/Clipboard.hpp +++ b/include/mglpp/window/Clipboard.hpp @@ -6,7 +6,7 @@ namespace mgl { class Clipboard { public: - static void set_string(std::string str); + static void set_string(const std::string &str); static std::string get_string(); }; } diff --git a/include/mglpp/window/Event.hpp b/include/mglpp/window/Event.hpp index 5b9e357..f3e9535 100644 --- a/include/mglpp/window/Event.hpp +++ b/include/mglpp/window/Event.hpp @@ -29,26 +29,35 @@ namespace mgl { bool system; }; - struct MouseMoveEvent { - int x; /* relative to left of the window */ - int y; /* relative to the top of the window */ - }; - struct MouseButtonEvent { Mouse::Button button; + int x; /* mouse position relative to left of the window */ + int y; /* mouse position relative to top of the window */ + }; + + struct MouseWheelScrollEvent { + int delta; /* positive = up, negative = down */ + int x; /* mouse position relative to left of the window */ + int y; /* mouse position relative to left of the window */ + }; + + struct MouseMoveEvent { int x; /* relative to left of the window */ - int y; /* relative to top of the window */ + int y; /* relative to the top of the window */ }; enum Type : int { Unknown, Closed, /* Window closed */ Resized, /* Window resized */ + LostFocus, + GainedFocus, TextEntered, KeyPressed, KeyReleased, MouseButtonPressed, MouseButtonReleased, + MouseWheelScrolled, MouseMoved }; @@ -59,6 +68,7 @@ namespace mgl { TextEvent text; KeyEvent key; MouseButtonEvent mouse_button; + MouseWheelScrollEvent mouse_wheel_scroll; MouseMoveEvent mouse_move; }; }; diff --git a/include/mglpp/window/Keyboard.hpp b/include/mglpp/window/Keyboard.hpp index b744143..17c4d7c 100644 --- a/include/mglpp/window/Keyboard.hpp +++ b/include/mglpp/window/Keyboard.hpp @@ -107,7 +107,10 @@ namespace mgl { F13, F14, F15, - Pause + Pause, + + /* This should always be the last key */ + __NumKeys__ }; }; } diff --git a/include/mglpp/window/Mouse.hpp b/include/mglpp/window/Mouse.hpp index c53f076..4fed4a9 100644 --- a/include/mglpp/window/Mouse.hpp +++ b/include/mglpp/window/Mouse.hpp @@ -11,7 +11,10 @@ namespace mgl { Right, Middle, XButton1, - XButton2 + XButton2, + + /* This should always be the last mouse button */ + __NumMouseButtons__ }; }; } diff --git a/include/mglpp/window/Window.hpp b/include/mglpp/window/Window.hpp index 2ef6526..1ce399c 100644 --- a/include/mglpp/window/Window.hpp +++ b/include/mglpp/window/Window.hpp @@ -4,7 +4,10 @@ #include "../graphics/PrimitiveType.hpp" #include "../graphics/Color.hpp" #include "../system/vec.hpp" +#include "Keyboard.hpp" +#include "Mouse.hpp" #include <stddef.h> +#include <string> extern "C" { #include <mgl/window/window.h> @@ -25,16 +28,19 @@ namespace mgl { class Window { public: - class Delegate { - public: - virtual ~Delegate() = default; - virtual void draw() = 0; + /* Has to match mgl_window_create_params */ + struct CreateParams { + mgl::vec2i position; + mgl::vec2i size; + mgl::vec2i min_size; /* (0, 0) = no limit */ + mgl::vec2i max_size; /* (0, 0) = no limit */ + WindowHandle parent_window = 0; /* 0 = root window */ }; Window(); ~Window(); - bool create(const char *title, int width, int height); + bool create(const char *title, CreateParams create_params); // Initialize this window from an existing window bool create(WindowHandle existing_window); @@ -53,7 +59,11 @@ namespace mgl { void set_key_repeat_enabled(bool enabled); void set_cursor_visible(bool visible); vec2i get_size() const; - vec2i get_cursor_position() const; + void set_size(mgl::vec2i size); + void set_position(mgl::vec2i position); + /* if |minimum| is (0, 0) then there is no minimum limit, if |maximum| is (0, 0) then there is no maximum limit */ + void set_size_limits(mgl::vec2i minimum, mgl::vec2i maximum); + vec2i get_mouse_position() const; /* This should be called every frame to retain the view. @@ -64,6 +74,12 @@ namespace mgl { void set_view(const View &new_view); View get_view(); + bool is_key_pressed(Keyboard::Key key) const; + bool is_mouse_button_pressed(Mouse::Button button) const; + + void set_clipboard(const std::string &str); + std::string get_clipboard(); + WindowHandle get_system_handle() const; private: mgl_window window; diff --git a/src/graphics/Font.cpp b/src/graphics/Font.cpp index ae87625..b3ef54c 100644 --- a/src/graphics/Font.cpp +++ b/src/graphics/Font.cpp @@ -1,5 +1,6 @@ #include "../../include/mglpp/graphics/Font.hpp" #include "../../include/mglpp/graphics/Texture.hpp" +#include "../../include/mglpp/system/MemoryMappedFile.hpp" #include <string.h> namespace mgl { @@ -11,32 +12,31 @@ namespace mgl { mgl_font_unload(&font); } - bool Font::load_from_file(const char *filepath, unsigned int character_size) { + bool Font::load_from_file(const MemoryMappedFile &mapped_file, unsigned int character_size) { if(font.texture.id) return false; - return mgl_font_load_from_file(&font, filepath, character_size) == 0; + return mgl_font_load_from_file(&font, mapped_file.internal_mapped_file(), character_size) == 0; } unsigned int Font::get_character_size() const { return font.character_size; } - FontGlyph Font::get_glyph(uint32_t codepoint) const { + FontGlyph Font::get_glyph(uint32_t codepoint) { FontGlyph font_glyph; - if(font.texture.id == 0) - return font_glyph; - mgl_font_get_glyph(&font, codepoint, (mgl_font_glyph*)&font_glyph); return font_glyph; } + int Font::get_kerning(uint32_t prev_codepoint, uint32_t codepoint) { + return mgl_font_get_kerning(&font, prev_codepoint, codepoint); + } + Texture Font::get_texture() const { - if(font.texture.id == 0) - return Texture(); return Texture::reference(font.texture); } mgl_font* Font::internal_font() { return &font; } -}
\ No newline at end of file +} diff --git a/src/graphics/Shader.cpp b/src/graphics/Shader.cpp index 7775b78..0d0e651 100644 --- a/src/graphics/Shader.cpp +++ b/src/graphics/Shader.cpp @@ -25,14 +25,10 @@ namespace mgl { } bool Shader::set_uniform(const char *name, float value) { - if(!shader_program.id) - return false; return mgl_shader_program_set_uniform_float(&shader_program, name, value) == 0; } bool Shader::set_uniform(const char *name, vec2f value) { - if(!shader_program.id) - return false; return mgl_shader_program_set_uniform_vec2f(&shader_program, name, { value.x, value.y }) == 0; } diff --git a/src/graphics/Sprite.cpp b/src/graphics/Sprite.cpp index b9066ee..e6cef73 100644 --- a/src/graphics/Sprite.cpp +++ b/src/graphics/Sprite.cpp @@ -9,7 +9,8 @@ namespace mgl { Sprite::Sprite() : Sprite(nullptr, vec2f(0.0f, 0.0f)) {} Sprite::Sprite(Texture *texture, vec2f position) : texture(texture) { - mgl_sprite_init(&sprite, texture ? texture->internal_texture() : nullptr, position.x, position.y); + mgl_sprite_init(&sprite, texture ? texture->internal_texture() : nullptr); + set_position(position); } Sprite::~Sprite() { @@ -41,14 +42,12 @@ namespace mgl { sprite.scale = { scale, scale }; } - // TODO: Implement void Sprite::set_rotation(float degrees) { - + mgl_sprite_set_rotation(&sprite, degrees); } - // TODO: Implement void Sprite::set_origin(vec2f origin) { - + mgl_sprite_set_origin(&sprite, *(mgl_vec2f*)&origin); } vec2f Sprite::get_scale() const { diff --git a/src/graphics/Text.cpp b/src/graphics/Text.cpp index 953833b..ad6fed2 100644 --- a/src/graphics/Text.cpp +++ b/src/graphics/Text.cpp @@ -76,9 +76,9 @@ namespace mgl { mgl_text_set_string(&text, this->str.c_str(), this->str.size()); } - // TODO: Implement vec2f Text::find_character_pos(size_t index) { - return vec2f(); + mgl_vec2f pos = mgl_text_find_character_pos(&text, index); + return vec2f(pos.x, pos.y); } Font* Text::get_font() { diff --git a/src/graphics/Texture.cpp b/src/graphics/Texture.cpp index cdaa3ba..f543c37 100644 --- a/src/graphics/Texture.cpp +++ b/src/graphics/Texture.cpp @@ -19,18 +19,32 @@ namespace mgl { return instance; } - bool Texture::load_from_file(const char *filepath) { + bool Texture::load_from_file(const char *filepath, const LoadOptions load_options) { if(texture.id) return false; - /* TODO: use the last arg (load options) */ - return mgl_texture_load_from_file(&texture, filepath, nullptr) == 0; + + if(mgl_texture_init(&texture) != 0) + return false; + + mgl_texture_load_options texture_load_options = { + load_options.compressed, + load_options.pixel_coordinates + }; + return mgl_texture_load_from_file(&texture, filepath, &texture_load_options) == 0; } - bool Texture::load_from_image(Image &image) { + bool Texture::load_from_image(Image &image, const LoadOptions load_options) { if(texture.id) return false; - /* TODO: use the last arg (load options) */ - return mgl_texture_load_from_image(&texture, image.internal_image(), nullptr) == 0; + + if(mgl_texture_init(&texture) != 0) + return false; + + mgl_texture_load_options texture_load_options = { + load_options.compressed, + load_options.pixel_coordinates + }; + return mgl_texture_load_from_image(&texture, image.internal_image(), &texture_load_options) == 0; } vec2i Texture::get_size() const { @@ -44,4 +58,4 @@ namespace mgl { mgl_texture* Texture::internal_texture() { return &texture; } -}
\ No newline at end of file +} diff --git a/src/system/MemoryMappedFile.cpp b/src/system/MemoryMappedFile.cpp new file mode 100644 index 0000000..54f15c1 --- /dev/null +++ b/src/system/MemoryMappedFile.cpp @@ -0,0 +1,36 @@ +#include "../../include/mglpp/system/MemoryMappedFile.hpp" + +namespace mgl { + MemoryMappedFile::MemoryMappedFile() { + memory_mapped_file.data = nullptr; + memory_mapped_file.size = 0; + memory_mapped_file.fd = -1; + } + + MemoryMappedFile::~MemoryMappedFile() { + mgl_mapped_file_unload(&memory_mapped_file); + } + + bool MemoryMappedFile::load(const char *filepath, LoadOptions load_options) { + if(memory_mapped_file.fd != -1) + return false; + + mgl_memory_mapped_file_load_options mapped_file_load_options = { + load_options.readable, + load_options.writable + }; + return mgl_mapped_file_load(filepath, &memory_mapped_file, &mapped_file_load_options) == 0; + } + + void* MemoryMappedFile::data() { + return memory_mapped_file.data; + } + + size_t MemoryMappedFile::size() { + return memory_mapped_file.size; + } + + const mgl_memory_mapped_file* MemoryMappedFile::internal_mapped_file() const { + return &memory_mapped_file; + } +}
\ No newline at end of file diff --git a/src/system/Utf8.cpp b/src/system/Utf8.cpp new file mode 100644 index 0000000..be9b2af --- /dev/null +++ b/src/system/Utf8.cpp @@ -0,0 +1,11 @@ +#include "../../include/mglpp/system/Utf8.hpp" + +extern "C" { +#include <mgl/system/utf8.h> +} + +namespace mgl { + bool utf8_decode(const unsigned char *str, size_t size, uint32_t *decoded_codepoint, size_t *codepoint_length) { + return mgl_utf8_decode(str, size, decoded_codepoint, codepoint_length); + } +}
\ No newline at end of file diff --git a/src/window/Clipboard.cpp b/src/window/Clipboard.cpp deleted file mode 100644 index b5b156e..0000000 --- a/src/window/Clipboard.cpp +++ /dev/null @@ -1,15 +0,0 @@ -#include "../../include/mglpp/window/Clipboard.hpp" - -namespace mgl { - // TODO: Implement - // static - void Clipboard::set_string(std::string str) { - - } - - // TODO: Implement - // static - std::string Clipboard::get_string() { - return ""; - } -}
\ No newline at end of file diff --git a/src/window/Window.cpp b/src/window/Window.cpp index 5dbbe5a..ee984fd 100644 --- a/src/window/Window.cpp +++ b/src/window/Window.cpp @@ -18,10 +18,10 @@ namespace mgl { mgl_window_deinit(&window); } - bool Window::create(const char *title, int width, int height) { + bool Window::create(const char *title, CreateParams create_params) { if(window.window) return false; - return mgl_window_create_with_params(&window, title, width, height, 0) == 0; + return mgl_window_create(&window, title, (mgl_window_create_params*)&create_params) == 0; } bool Window::create(WindowHandle existing_window) { @@ -31,14 +31,10 @@ namespace mgl { } bool Window::poll_event(Event &event) { - if(!window.window) - return false; return mgl_window_poll_event(&window, (mgl_event*)&event); } void Window::clear(Color color) { - if(!window.window) - return; mgl_window_clear(&window, mgl_color{color.r, color.g, color.b, color.a}); } @@ -64,36 +60,27 @@ namespace mgl { } void Window::display() { - if(!window.window) - return; mgl_window_display(&window); } - // TODO: Implement bool Window::is_open() const { - if(!window.window) - return false; return mgl_window_is_open(&window); } - // TODO: Implement bool Window::has_focus() const { - return true; + return mgl_window_has_focus(&window); } - // TODO: Implement void Window::close() { - + mgl_window_close(&window); } - // TODO: Implement void Window::set_title(const char *title) { - + mgl_window_set_title(&window, title); } - // TODO: Implement void Window::set_framerate_limit(unsigned int fps) { - + mgl_window_set_framerate_limit(&window, fps); } // TODO: Implement @@ -101,33 +88,63 @@ namespace mgl { } - // TODO: Implement void Window::set_cursor_visible(bool visible) { - + mgl_window_set_cursor_visible(&window, visible); } vec2i Window::get_size() const { return { window.size.x, window.size.y }; } - vec2i Window::get_cursor_position() const { + void Window::set_size(mgl::vec2i size) { + mgl_window_set_size(&window, { size.x, size.y }); + } + + void Window::set_position(mgl::vec2i position) { + mgl_window_set_position(&window, { position.x, position.y }); + } + + void Window::set_size_limits(mgl::vec2i minimum, mgl::vec2i maximum) { + mgl_window_set_size_limits(&window, { minimum.x, minimum.y }, { maximum.x, maximum.y }); + } + + vec2i Window::get_mouse_position() const { return { window.cursor_position.x, window.cursor_position.y }; } void Window::set_view(const View &new_view) { - if(!window.window) - return; mgl_window_set_view(&window, (mgl_view*)&new_view); } View Window::get_view() { View view; - if(!window.window) - return view; mgl_window_get_view(&window, (mgl_view*)&view); return view; } + bool Window::is_key_pressed(Keyboard::Key key) const { + return mgl_window_is_key_pressed(&window, (mgl_key)key); + } + + bool Window::is_mouse_button_pressed(Mouse::Button button) const { + return mgl_window_is_mouse_button_pressed(&window, (mgl_mouse_button)button); + } + + void Window::set_clipboard(const std::string &str) { + mgl_window_set_clipboard(&window, str.c_str(), str.size()); + } + + std::string Window::get_clipboard() { + std::string result; + char *str = nullptr; + size_t size = 0; + if(mgl_window_get_clipboard(&window, &str, &size)) { + result.assign(str, size); + free(str); + } + return result; + } + WindowHandle Window::get_system_handle() const { return window.window; } diff --git a/tests/main.cpp b/tests/main.cpp index 25ef012..f3ad539 100644 --- a/tests/main.cpp +++ b/tests/main.cpp @@ -11,12 +11,13 @@ #include <mglpp/graphics/Vertex.hpp> #include <mglpp/graphics/Shader.hpp> #include <mglpp/system/Clock.hpp> +#include <mglpp/system/MemoryMappedFile.hpp> struct Delegate { Delegate() {} void draw() { - mgl::Rectangle rect(window->get_cursor_position().to_vec2f(), { 100.0f, 500.0f }); + mgl::Rectangle rect(window->get_mouse_position().to_vec2f(), { 100.0f, 500.0f }); rect.set_color({255, 0, 0, 255}); window->draw(rect); @@ -29,7 +30,7 @@ struct Delegate { mgl::Text text("hello world!\nelapsed time: " + std::to_string(clock.get_elapsed_time_seconds()), { 0.0f, 0.0f }, *font); window->draw(text); - vertex_buffer->set_position({ window->get_cursor_position().x + 100, window->get_cursor_position().y }); + vertex_buffer->set_position({ (float)window->get_mouse_position().x + 100, (float)window->get_mouse_position().y }); window->draw(*vertex_buffer); } @@ -44,16 +45,22 @@ struct Delegate { int main(int argc, char **argv) { mgl::Init init; + mgl::Window::CreateParams window_create_params; + window_create_params.size = { 1280, 720 }; mgl::Window window; - if(!window.create("mglpp", 1920, 1080)) + if(!window.create("mglpp", window_create_params)) return 1; mgl::Texture texture; if(!texture.load_from_file("depends/mgl/tests/X11.jpg")) return 1; + mgl::MemoryMappedFile font_file; + if(!font_file.load("/usr/share/fonts/noto/NotoSans-Regular.ttf", mgl::MemoryMappedFile::LoadOptions{true, false})) + return 1; + mgl::Font font; - if(!font.load_from_file("/usr/share/fonts/noto/NotoSans-Regular.ttf", 32)) + if(!font.load_from_file(font_file, 32)) return 1; mgl::Shader shader; |