Compare commits
No commits in common. "ad73f0c9219448e1e703105d0b66741a14a46311" and "3edd2ac5c5d3e2238218e8b8c64071410c41e8a5" have entirely different histories.
ad73f0c921
...
3edd2ac5c5
27 changed files with 421 additions and 577 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -3,4 +3,3 @@ out
|
|||
.idea
|
||||
cmake-build-debug
|
||||
build
|
||||
**/.DS_Store
|
||||
|
|
6
.gitmodules
vendored
6
.gitmodules
vendored
|
@ -17,9 +17,9 @@
|
|||
[submodule "Keishiki/ext/fmt"]
|
||||
path = Keishiki/ext/fmt
|
||||
url = https://github.com/fmtlib/fmt.git
|
||||
[submodule "Keishiki/ext/glaze"]
|
||||
path = Keishiki/ext/glaze
|
||||
url = https://github.com/stephenberry/glaze.git
|
||||
[submodule "Keishiki/ext/vg-renderer"]
|
||||
path = Keishiki/ext/vg-renderer
|
||||
url = https://github.com/jdryg/vg-renderer.git
|
||||
[submodule "Keishiiki/ext/SDL"]
|
||||
path = Keishiki/ext/SDL
|
||||
url = https://github.com/libsdl-org/SDL.git
|
||||
|
|
|
@ -1,51 +0,0 @@
|
|||
#include <Actions.h>
|
||||
#include <VisualTrack.h>
|
||||
|
||||
namespace K {
|
||||
void AddTransformLayer(CompositionState& s, const String& name) {
|
||||
auto l = Layer{
|
||||
VisualTrack{},
|
||||
name,
|
||||
Graphics::K_V_AlphaOver,
|
||||
0UL,
|
||||
s.frame_max
|
||||
};
|
||||
l.track.AddUniform("u_resolution", ShaderGraph::ExpandVariant(ShaderGraph::T_XY), K_U_Exposed);
|
||||
l.track.uniforms[0].val = ShaderGraph::T_Map<ShaderGraph::T_XY>::type{static_cast<f32>(s.width), static_cast<f32>(s.height)};
|
||||
VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_opacity", ShaderGraph::ExpandVariant(ShaderGraph::T_Float), K_U_Exposed);
|
||||
l.track.uniforms[1].val = ShaderGraph::T_Map<ShaderGraph::T_Float>::type(1.0f);
|
||||
VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_rot", ShaderGraph::ExpandVariant(ShaderGraph::T_Float), K_U_Exposed);
|
||||
l.track.uniforms[2].val = ShaderGraph::T_Map<ShaderGraph::T_Float>::type(.0f);
|
||||
VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_scale", ShaderGraph::ExpandVariant(ShaderGraph::T_XY), K_U_Exposed);
|
||||
l.track.uniforms[3].val = ShaderGraph::T_Map<ShaderGraph::T_XY>::type{1.0f, 1.0f};
|
||||
VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_translate", ShaderGraph::ExpandVariant(ShaderGraph::T_XY), K_U_Exposed);
|
||||
l.track.uniforms[4].val = ShaderGraph::T_Map<ShaderGraph::T_XY>::type{.0f, .0f};
|
||||
VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.shader = "void main() {\n"
|
||||
"\tfloat angle = -u_rot * M_PI / 180.0f;\n"
|
||||
"\tvec2 uv = vec2(v_texcoord0.x, 1.0f - v_texcoord0.y) - .5f;\n"
|
||||
"\tuv = uv * u_resolution;\n"
|
||||
"\tuv = uv - u_translate;\n"
|
||||
"\tuv = vec2(cos(angle)*uv.x - sin(angle)*uv.y, sin(angle)*uv.x + cos(angle)*uv.y);\n"
|
||||
"\tuv = uv / s_texColor_dims;\n"
|
||||
"\tuv = uv / u_scale;\n"
|
||||
"\tuv = uv + .5f;\n\n"
|
||||
"\tvec4 tx = texture2D(s_texColor, uv);\n"
|
||||
"\tgl_FragColor = vec4(tx.rgb, tx.a * u_opacity);\n"
|
||||
"}\n";
|
||||
|
||||
l.track.AddSampler("s_texColor");
|
||||
|
||||
l.track.Compile();
|
||||
s.layers.push_back(std::move(l));
|
||||
}
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
# CMakeList.txt : CMake project for Keishiki, include source and define
|
||||
# CMakeList.txt : CMake project for Keishiki, include source and define
|
||||
# project specific logic here.
|
||||
#
|
||||
cmake_minimum_required (VERSION 3.16)
|
||||
|
@ -20,7 +20,9 @@ include_directories ("include" "include/ext" "ext/imgui" "ext/implot" "ext/plf_c
|
|||
|
||||
add_subdirectory("ext/SDL")
|
||||
add_subdirectory("ext/fmt")
|
||||
# add_subdirectory("ext/glaze")
|
||||
# add_subdirectory("ext/freetype")
|
||||
# add_compile_definitions(WL_EGL_PLATFORM)
|
||||
add_subdirectory("ext/bgfx")
|
||||
|
||||
add_compile_definitions(IMGUI_DEFINE_MATH_OPERATORS)
|
||||
|
@ -39,7 +41,11 @@ if (WIN32)
|
|||
include_directories("include/windows")
|
||||
target_link_libraries (Keishiki PRIVATE freetype bgfx bx ${PROJECT_SOURCE_DIR}/lib/x64/SDL2.lib ${PROJECT_SOURCE_DIR}/lib/x64/SDL2main.lib)
|
||||
elseif (APPLE)
|
||||
target_link_libraries (Keishiki PRIVATE bgfx bx SDL3::SDL3 fmt)
|
||||
target_link_libraries (Keishiki PRIVATE freetype bgfx bx SDL3::SDL3 fmt glaze_glaze)
|
||||
else ()
|
||||
target_link_libraries (Keishiki PRIVATE bgfx bx SDL3::SDL3 fmt)
|
||||
find_package(SDL3 REQUIRED CONFIG REQUIRED COMPONENTS SDL3-shared)
|
||||
find_package(ECM REQUIRED NO_MODULE)
|
||||
set(CMAKE_MODULE_PATH ${ECM_FIND_MODULE_DIR})
|
||||
find_package(Wayland REQUIRED Egl)
|
||||
target_link_libraries (Keishiki PRIVATE freetype bgfx bx SDL3::SDL3 ${Wayland_LIBRARIES} fmt glaze_glaze)
|
||||
endif ()
|
||||
|
|
|
@ -2,8 +2,11 @@
|
|||
#include "Graphics.h"
|
||||
#include "UI.h"
|
||||
|
||||
#if BX_PLATFORM_LINUX && WL_EGL_PLATFORM
|
||||
#include <wayland-egl.h>
|
||||
#endif
|
||||
|
||||
#include <SDL3/SDL.h>
|
||||
#include <SDL3/SDL_main.h>
|
||||
#include <SDL3/SDL_timer.h>
|
||||
|
||||
#include <bgfx/bgfx.h>
|
||||
|
@ -13,20 +16,17 @@
|
|||
#include <imgui.h>
|
||||
|
||||
namespace K {
|
||||
constexpr auto RESET_FLAGS = BGFX_RESET_VSYNC | BGFX_RESET_HIDPI;
|
||||
|
||||
bool Init() {
|
||||
if (!SDL_Init(SDL_INIT_VIDEO)) {
|
||||
#if BX_PLATFORM_LINUX && !WL_EGL_PLATFORM
|
||||
SDL_SetHint(SDL_HINT_VIDEO_DRIVER, "x11");
|
||||
#endif
|
||||
if (SDL_Init(SDL_INIT_VIDEO)) {
|
||||
Log(K_L_Error, "{}", SDL_GetError());
|
||||
return false;
|
||||
}
|
||||
|
||||
app_state.window = SDL_CreateWindow("Keishiki", app_state.window_width, app_state.window_height, SDL_WINDOW_HIGH_PIXEL_DENSITY);
|
||||
if (app_state.window == nullptr) {
|
||||
Log(K_L_Error, "{}", SDL_GetError());
|
||||
return false;
|
||||
}
|
||||
|
||||
SDL_SetWindowResizable(app_state.window, true);
|
||||
i32 display_n;
|
||||
SDL_DisplayID *ids = SDL_GetDisplays(&display_n);
|
||||
|
@ -34,31 +34,36 @@ namespace K {
|
|||
SDL_free(ids);
|
||||
app_state.window_width *= app_state.dpi_scale;
|
||||
app_state.window_height *= app_state.dpi_scale;
|
||||
|
||||
if (app_state.window == nullptr) {
|
||||
Log(K_L_Error, "{}", SDL_GetError());
|
||||
return false;
|
||||
}
|
||||
|
||||
bgfx::Init bgfxInit;
|
||||
bgfxInit.type = bgfx::RendererType::Count; // Automatically choose a renderer.
|
||||
bgfxInit.resolution.width = app_state.window_width;
|
||||
bgfxInit.resolution.height = app_state.window_height;
|
||||
bgfxInit.resolution.reset = RESET_FLAGS;
|
||||
bgfxInit.resolution.reset = BGFX_RESET_VSYNC | BGFX_RESET_HIDPI;
|
||||
|
||||
#if BX_PLATFORM_WINDOWS
|
||||
bgfxInit.platformData.nwh = SDL_GetPointerProperty(SDL_GetWindowProperties(window), SDL_PROP_WINDOW_WIN32_HWND_POINTER, NULL);
|
||||
bgfxInit.platformData.nwh = SDL_GetProperty(SDL_GetWindowProperties(window), SDL_PROP_WINDOW_WIN32_HWND_POINTER, NULL);
|
||||
#elif BX_PLATFORM_OSX
|
||||
bgfxInit.platformData.nwh = SDL_GetPointerProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_COCOA_WINDOW_POINTER, NULL);
|
||||
bgfxInit.platformData.nwh = SDL_GetProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_COCOA_WINDOW_POINTER, NULL);
|
||||
bgfx::renderFrame();
|
||||
#elif BX_PLATFORM_LINUX
|
||||
if (SDL_strcmp(SDL_GetCurrentVideoDriver(), "x11") == 0) {
|
||||
bgfxInit.platformData.ndt = SDL_GetPointerProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_X11_DISPLAY_POINTER, NULL);
|
||||
bgfxInit.platformData.ndt = SDL_GetProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_X11_DISPLAY_POINTER, NULL);
|
||||
bgfxInit.platformData.nwh = (void*)SDL_GetNumberProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_X11_WINDOW_NUMBER, 0);
|
||||
}
|
||||
#if WL_EGL_PLATFORM
|
||||
else if (SDL_strcmp(SDL_GetCurrentVideoDriver(), "wayland") == 0) {
|
||||
bgfxInit.platformData.type = bgfx::NativeWindowHandleType::Wayland;
|
||||
bgfxInit.platformData.ndt = SDL_GetPointerProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_DISPLAY_POINTER, NULL);
|
||||
bgfxInit.platformData.nwh = SDL_GetPointerProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_EGL_WINDOW_POINTER, NULL);
|
||||
bgfxInit.platformData.ndt = SDL_GetProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_DISPLAY_POINTER, NULL);
|
||||
bgfxInit.platformData.nwh = SDL_GetProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_EGL_WINDOW_POINTER, NULL);
|
||||
if (!bgfxInit.platformData.nwh) {
|
||||
bgfxInit.platformData.nwh = wl_egl_window_create((struct wl_surface *)SDL_GetPointerProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_SURFACE_POINTER, NULL), app_state.window_width, app_state.window_height);
|
||||
SDL_SetPointerProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_EGL_WINDOW_POINTER, (void*)(uintptr_t)bgfxInit.platformData.nwh);
|
||||
bgfxInit.platformData.nwh = wl_egl_window_create((struct wl_surface *)SDL_GetProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_SURFACE_POINTER, NULL), app_state.window_width, app_state.window_height);
|
||||
SDL_SetProperty(SDL_GetWindowProperties(app_state.window), SDL_PROP_WINDOW_WAYLAND_EGL_WINDOW_POINTER, (void*)(uintptr_t)bgfxInit.platformData.nwh);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
@ -100,7 +105,7 @@ namespace K {
|
|||
if (current_event.type == SDL_EVENT_WINDOW_PIXEL_SIZE_CHANGED) {
|
||||
app_state.window_width = current_event.window.data1;
|
||||
app_state.window_height = current_event.window.data2;
|
||||
bgfx::reset(current_event.window.data1, current_event.window.data2, RESET_FLAGS);
|
||||
bgfx::reset(current_event.window.data1, current_event.window.data2, BGFX_RESET_VSYNC | BGFX_RESET_HIDPI);
|
||||
UI::SetLogoView();
|
||||
}
|
||||
}
|
||||
|
@ -116,7 +121,11 @@ namespace K {
|
|||
K::UI::Shutdown();
|
||||
K::Resource::Shutdown();
|
||||
bgfx::shutdown();
|
||||
|
||||
#if !(BX_PLATFORM_LINUX && WL_EGL_PLATFORM)
|
||||
SDL_DestroyWindow(app_state.window);
|
||||
#endif
|
||||
|
||||
SDL_Quit();
|
||||
}
|
||||
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
#include "Graphics.h"
|
||||
#include <Keishiki.h>
|
||||
#include <Resource.h>
|
||||
//#include <ft2build.h>
|
||||
//#include FT_FREETYPE_H
|
||||
#include <ft2build.h>
|
||||
#include FT_FREETYPE_H
|
||||
|
||||
#include <bx/math.h>
|
||||
|
||||
|
@ -30,94 +30,94 @@ namespace {
|
|||
1, 2, 3
|
||||
};
|
||||
|
||||
// FT_Library library;
|
||||
// FT_Error error;
|
||||
//
|
||||
// struct Glyph {
|
||||
// bgfx::TextureHandle tex = { bgfx::kInvalidHandle };
|
||||
// u32 w = 0, h = 0;
|
||||
// i32 x = 0, y = 0, adv_x = 0, adv_y = 0;
|
||||
// };
|
||||
//
|
||||
// struct Font {
|
||||
// FT_Face face = nullptr;
|
||||
// K::Dict<K::Char, Glyph> cache{};
|
||||
//
|
||||
// Glyph& get_char(K::Char c) {
|
||||
// if (cache.find(c) == cache.end()) {
|
||||
// FT_GlyphSlot slot = face->glyph;
|
||||
//
|
||||
// error = FT_Load_Char(face, c, FT_LOAD_RENDER);
|
||||
// if (error) {
|
||||
// K::Log(K::K_L_Error, "Failed to load character");
|
||||
// }
|
||||
//
|
||||
// if (slot->bitmap.width != 0) {
|
||||
// const bgfx::Memory *buf = bgfx::copy(slot->bitmap.buffer, slot->bitmap.pitch * slot->bitmap.rows);
|
||||
//
|
||||
// cache.emplace(c, Glyph{
|
||||
// bgfx::createTexture2D(
|
||||
// slot->bitmap.width,
|
||||
// slot->bitmap.rows,
|
||||
// false,
|
||||
// 1,
|
||||
// bgfx::TextureFormat::A8,
|
||||
// BGFX_TEXTURE_NONE | BGFX_SAMPLER_UVW_CLAMP,
|
||||
// buf
|
||||
// ),
|
||||
// slot->bitmap.width,
|
||||
// slot->bitmap.rows,
|
||||
// slot->bitmap_left,
|
||||
// slot->bitmap_top,
|
||||
// static_cast<i32>(slot->advance.x),
|
||||
// static_cast<i32>(slot->advance.y)
|
||||
// });
|
||||
// }
|
||||
// else cache.emplace(c, Glyph{
|
||||
// { bgfx::kInvalidHandle },
|
||||
// 0,
|
||||
// 0,
|
||||
// 0,
|
||||
// 0,
|
||||
// static_cast<i32>(slot->advance.x),
|
||||
// static_cast<i32>(slot->advance.y)
|
||||
// });
|
||||
// }
|
||||
// return cache[c];
|
||||
// }
|
||||
// };
|
||||
//
|
||||
// std::optional<Font> GetFont(const char *path) {
|
||||
// Font f;
|
||||
//
|
||||
// error = FT_New_Face(library, path, 0, &f.face);
|
||||
// if (error == FT_Err_Unknown_File_Format) {
|
||||
// K::Log(K::K_L_Error, "FreeType Unknown_File_Format");
|
||||
// return std::nullopt;
|
||||
// }
|
||||
// else if (error) {
|
||||
// K::Log(K::K_L_Error, "FreeType font loading error");
|
||||
// return std::nullopt;
|
||||
// }
|
||||
//
|
||||
// error = FT_Set_Char_Size(f.face, 0, 20 * 64, 72, 72);
|
||||
// if (error) {
|
||||
// K::Log(K::K_L_Error, "FreeType Set_Char_Size error");
|
||||
// return std::nullopt;
|
||||
// }
|
||||
//
|
||||
// return f;
|
||||
// }
|
||||
//
|
||||
// void DestroyFont(Font& f) {
|
||||
// FT_Done_Face(f.face);
|
||||
// for (auto & it : f.cache) {
|
||||
// if (isValid(it.second.tex))
|
||||
// bgfx::destroy(it.second.tex);
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// Font regular, bold;
|
||||
FT_Library library;
|
||||
FT_Error error;
|
||||
|
||||
struct Glyph {
|
||||
bgfx::TextureHandle tex = { bgfx::kInvalidHandle };
|
||||
u32 w = 0, h = 0;
|
||||
i32 x = 0, y = 0, adv_x = 0, adv_y = 0;
|
||||
};
|
||||
|
||||
struct Font {
|
||||
FT_Face face = nullptr;
|
||||
K::Dict<K::Char, Glyph> cache{};
|
||||
|
||||
Glyph& get_char(K::Char c) {
|
||||
if (cache.find(c) == cache.end()) {
|
||||
FT_GlyphSlot slot = face->glyph;
|
||||
|
||||
error = FT_Load_Char(face, c, FT_LOAD_RENDER);
|
||||
if (error) {
|
||||
K::Log(K::K_L_Error, "Failed to load character");
|
||||
}
|
||||
|
||||
if (slot->bitmap.width != 0) {
|
||||
const bgfx::Memory *buf = bgfx::copy(slot->bitmap.buffer, slot->bitmap.pitch * slot->bitmap.rows);
|
||||
|
||||
cache.emplace(c, Glyph{
|
||||
bgfx::createTexture2D(
|
||||
slot->bitmap.width,
|
||||
slot->bitmap.rows,
|
||||
false,
|
||||
1,
|
||||
bgfx::TextureFormat::A8,
|
||||
BGFX_TEXTURE_NONE | BGFX_SAMPLER_UVW_CLAMP,
|
||||
buf
|
||||
),
|
||||
slot->bitmap.width,
|
||||
slot->bitmap.rows,
|
||||
slot->bitmap_left,
|
||||
slot->bitmap_top,
|
||||
static_cast<i32>(slot->advance.x),
|
||||
static_cast<i32>(slot->advance.y)
|
||||
});
|
||||
}
|
||||
else cache.emplace(c, Glyph{
|
||||
{ bgfx::kInvalidHandle },
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
0,
|
||||
static_cast<i32>(slot->advance.x),
|
||||
static_cast<i32>(slot->advance.y)
|
||||
});
|
||||
}
|
||||
return cache[c];
|
||||
}
|
||||
};
|
||||
|
||||
std::optional<Font> GetFont(const char *path) {
|
||||
Font f;
|
||||
|
||||
error = FT_New_Face(library, path, 0, &f.face);
|
||||
if (error == FT_Err_Unknown_File_Format) {
|
||||
K::Log(K::K_L_Error, "FreeType Unknown_File_Format");
|
||||
return std::nullopt;
|
||||
}
|
||||
else if (error) {
|
||||
K::Log(K::K_L_Error, "FreeType font loading error");
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
error = FT_Set_Char_Size(f.face, 0, 20 * 64, 72, 72);
|
||||
if (error) {
|
||||
K::Log(K::K_L_Error, "FreeType Set_Char_Size error");
|
||||
return std::nullopt;
|
||||
}
|
||||
|
||||
return f;
|
||||
}
|
||||
|
||||
void DestroyFont(Font& f) {
|
||||
FT_Done_Face(f.face);
|
||||
for (auto & it : f.cache) {
|
||||
if (isValid(it.second.tex))
|
||||
bgfx::destroy(it.second.tex);
|
||||
}
|
||||
}
|
||||
|
||||
Font regular, bold;
|
||||
bgfx::ProgramHandle imga_program;
|
||||
bgfx::ProgramHandle a_program;
|
||||
|
||||
|
@ -135,15 +135,15 @@ namespace {
|
|||
|
||||
namespace K::Graphics {
|
||||
bool Init() {
|
||||
// error = FT_Init_FreeType(&library);
|
||||
// if (error) {
|
||||
// Log(K_L_Info, "FreeType init error: {}", error);
|
||||
// return false;
|
||||
// }
|
||||
error = FT_Init_FreeType(&library);
|
||||
if (error) {
|
||||
Log(K_L_Info, "FreeType init error: {}", error);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (auto f = GetFont("SourceHanSans-Regular.ttc")) regular = *f; else return false;
|
||||
if (auto f = GetFont("SourceHanSans-Bold.ttc")) bold = *f; else return false;
|
||||
|
||||
// if (auto f = GetFont("SourceHanSans-Regular.ttc")) regular = *f; else return false;
|
||||
// if (auto f = GetFont("SourceHanSans-Bold.ttc")) bold = *f; else return false;
|
||||
//
|
||||
pcvDecl.begin()
|
||||
.add(bgfx::Attrib::Position, 3, bgfx::AttribType::Float)
|
||||
.add(bgfx::Attrib::TexCoord0, 2, bgfx::AttribType::Float)
|
||||
|
@ -167,9 +167,9 @@ namespace K::Graphics {
|
|||
}
|
||||
|
||||
void Shutdown() {
|
||||
// DestroyFont(regular);
|
||||
// DestroyFont(bold);
|
||||
// FT_Done_FreeType(library);
|
||||
DestroyFont(regular);
|
||||
DestroyFont(bold);
|
||||
FT_Done_FreeType(library);
|
||||
|
||||
bgfx::destroy(imga_program);
|
||||
bgfx::destroy(a_program);
|
||||
|
@ -227,130 +227,130 @@ namespace K::Graphics {
|
|||
DrawTexture(view_id, tex, pos_x, pos_y, w, h, (BGFX_STATE_DEFAULT | BGFX_STATE_BLEND_ALPHA) & ~(BGFX_STATE_WRITE_Z | BGFX_STATE_DEPTH_TEST_LESS), a_program);
|
||||
}
|
||||
|
||||
// void WalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y) {
|
||||
// Font *f = ®ular;
|
||||
//
|
||||
// auto& [tx, w, h, l, t, x, y] = f->get_char(c);
|
||||
//
|
||||
// pos_x += l;
|
||||
//
|
||||
// pos_x += x >> 6;
|
||||
// pos_y += y >> 6;
|
||||
// }
|
||||
//
|
||||
// void RenderWalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y, u32 col) {
|
||||
// Font *f = ®ular;
|
||||
//
|
||||
// auto& [tx, w, h, l, t, x, y] = f->get_char(c);
|
||||
//
|
||||
// pos_x += l;
|
||||
//
|
||||
// if (isValid(tx) && w != 0) {
|
||||
// DrawTextureStencilAlpha(view_id, tx, pos_x, pos_y - (h - t), w, h);
|
||||
// }
|
||||
//
|
||||
// pos_x += x >> 6;
|
||||
// pos_y += y >> 6;
|
||||
// }
|
||||
//
|
||||
// void RenderGlyph(u32 view_id, Char c, i32 pos_x, i32 pos_y, u32 col) {
|
||||
// Font *f = ®ular;
|
||||
//
|
||||
// auto& [tx, w, h, l, t, x, y] = f->get_char(c);
|
||||
//
|
||||
// pos_x += l;
|
||||
//
|
||||
// if (isValid(tx) && w != 0) {
|
||||
// DrawTextureStencilAlpha(view_id, tx, pos_x, pos_y - (h - t), w, h);
|
||||
// }
|
||||
//
|
||||
// pos_x += x >> 6;
|
||||
// pos_y += y >> 6;
|
||||
// }
|
||||
//
|
||||
// void WalkString(u32 view_id, const String& s, i32& pos_x, i32& pos_y) {
|
||||
// for (const auto& c : s)
|
||||
// WalkGlyph(view_id, c, pos_x, pos_y);
|
||||
// }
|
||||
//
|
||||
// void RenderString(u32 view_id, const String& s, i32 pos_x, i32 pos_y, u32 col) {
|
||||
// for (const auto& c : s)
|
||||
// RenderWalkGlyph(view_id, c, pos_x, pos_y, col);
|
||||
// }
|
||||
//
|
||||
// void WalkString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32& pos_x, i32& pos_y) {
|
||||
// while (cbegin < cend)
|
||||
// WalkGlyph(view_id, *cbegin++, pos_x, pos_y);
|
||||
// }
|
||||
//
|
||||
// void RenderString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32 pos_x, i32 pos_y, u32 col) {
|
||||
// while (cbegin < cend)
|
||||
// RenderGlyph(view_id, *cbegin++, pos_x, pos_y, col);
|
||||
// }
|
||||
//
|
||||
// void RenderStringCentered(u32 view_id, const String& s, i32 pos_x, i32 pos_y, u32 col) {
|
||||
// i32 copy_x = 0, copy_y = 0;
|
||||
// WalkString(view_id, s, copy_x, copy_y);
|
||||
// RenderString(view_id, s, pos_x - copy_x / 2, pos_y, col);
|
||||
// }
|
||||
//
|
||||
// // I cannot reason this function, returns where the string would end if it was not halted
|
||||
// i32 RenderSubstringBox(u32 view_id, const String& s, i32& pos_x, i32& pos_y, i32 reset_x, u32 w, u32 col, size_t s_end) {
|
||||
// Font *f = ®ular;
|
||||
//
|
||||
// String::const_iterator last = s.cbegin(), end = s.cend(), pos = std::find(last, end, u' '),
|
||||
// halt = s_end > s.length() ? end : last + s_end;
|
||||
// if (pos == end) { // Render the entire thing with hard break if we don't split at all
|
||||
// String::const_iterator last_copy = last;
|
||||
// i32 copy_x = pos_x, copy_y = pos_y;
|
||||
// while (last != std::min(pos, halt)) {
|
||||
// RenderGlyph(view_id, *last++, pos_x, pos_y, col);
|
||||
// if (pos_x - reset_x > w) {
|
||||
// pos_x = reset_x;
|
||||
// pos_y -= f->face->size->metrics.height / 64;
|
||||
// }
|
||||
// if (last >= halt) {
|
||||
// WalkString(view_id, last_copy, pos, copy_x, copy_y);
|
||||
// return copy_x;
|
||||
// };
|
||||
// }
|
||||
// }
|
||||
// else while (last != end) { // Loop through all segments
|
||||
// i32 copy_x = pos_x, old_x = pos_x, copy_y = pos_y;
|
||||
// WalkString(view_id, last, pos, copy_x, copy_y);
|
||||
// if (copy_x - reset_x > w) { // if walk exceeded max w
|
||||
// copy_x = reset_x, copy_y = pos_y; // try walk again from leftmost of box, see if a soft break works; reset y from last walk
|
||||
// WalkString(view_id, last, pos, copy_x, copy_y);
|
||||
// if (copy_x - reset_x > w) { // soft break won't work, go back to old x and hard break
|
||||
// pos_x = old_x;
|
||||
// while (last != pos) {
|
||||
// RenderGlyph(view_id, *last++, pos_x, pos_y, col);
|
||||
// if (pos_x - reset_x > w) {
|
||||
// pos_x = reset_x;
|
||||
// pos_y -= f->face->size->metrics.height / 64;
|
||||
// }
|
||||
// if (last >= halt) return copy_x;
|
||||
// }
|
||||
// }
|
||||
// else { // soft break and kill beginning space
|
||||
// pos_x = reset_x;
|
||||
// pos_y -= f->face->size->metrics.height / 64;
|
||||
// last++;
|
||||
// RenderString(view_id, last, std::min(pos, halt), pos_x, pos_y, col);
|
||||
// if (last >= halt) return copy_x;
|
||||
// }
|
||||
// }
|
||||
// else {
|
||||
// RenderString(view_id, last, std::min(pos, halt), pos_x, pos_y, col);
|
||||
// if (last >= halt) return copy_x;
|
||||
// }
|
||||
//
|
||||
// last = pos;
|
||||
// if (pos != end)
|
||||
// pos = std::find(std::next(pos), end, ' ');
|
||||
// }
|
||||
// return pos_x;
|
||||
// }
|
||||
void WalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y) {
|
||||
Font *f = ®ular;
|
||||
|
||||
auto& [tx, w, h, l, t, x, y] = f->get_char(c);
|
||||
|
||||
pos_x += l;
|
||||
|
||||
pos_x += x >> 6;
|
||||
pos_y += y >> 6;
|
||||
}
|
||||
|
||||
void RenderWalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y, u32 col) {
|
||||
Font *f = ®ular;
|
||||
|
||||
auto& [tx, w, h, l, t, x, y] = f->get_char(c);
|
||||
|
||||
pos_x += l;
|
||||
|
||||
if (isValid(tx) && w != 0) {
|
||||
DrawTextureStencilAlpha(view_id, tx, pos_x, pos_y - (h - t), w, h);
|
||||
}
|
||||
|
||||
pos_x += x >> 6;
|
||||
pos_y += y >> 6;
|
||||
}
|
||||
|
||||
void RenderGlyph(u32 view_id, Char c, i32 pos_x, i32 pos_y, u32 col) {
|
||||
Font *f = ®ular;
|
||||
|
||||
auto& [tx, w, h, l, t, x, y] = f->get_char(c);
|
||||
|
||||
pos_x += l;
|
||||
|
||||
if (isValid(tx) && w != 0) {
|
||||
DrawTextureStencilAlpha(view_id, tx, pos_x, pos_y - (h - t), w, h);
|
||||
}
|
||||
|
||||
pos_x += x >> 6;
|
||||
pos_y += y >> 6;
|
||||
}
|
||||
|
||||
void WalkString(u32 view_id, const String& s, i32& pos_x, i32& pos_y) {
|
||||
for (const auto& c : s)
|
||||
WalkGlyph(view_id, c, pos_x, pos_y);
|
||||
}
|
||||
|
||||
void RenderString(u32 view_id, const String& s, i32 pos_x, i32 pos_y, u32 col) {
|
||||
for (const auto& c : s)
|
||||
RenderWalkGlyph(view_id, c, pos_x, pos_y, col);
|
||||
}
|
||||
|
||||
void WalkString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32& pos_x, i32& pos_y) {
|
||||
while (cbegin < cend)
|
||||
WalkGlyph(view_id, *cbegin++, pos_x, pos_y);
|
||||
}
|
||||
|
||||
void RenderString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32 pos_x, i32 pos_y, u32 col) {
|
||||
while (cbegin < cend)
|
||||
RenderGlyph(view_id, *cbegin++, pos_x, pos_y, col);
|
||||
}
|
||||
|
||||
void RenderStringCentered(u32 view_id, const String& s, i32 pos_x, i32 pos_y, u32 col) {
|
||||
i32 copy_x = 0, copy_y = 0;
|
||||
WalkString(view_id, s, copy_x, copy_y);
|
||||
RenderString(view_id, s, pos_x - copy_x / 2, pos_y, col);
|
||||
}
|
||||
|
||||
// I cannot reason this function, returns where the string would end if it was not halted
|
||||
i32 RenderSubstringBox(u32 view_id, const String& s, i32& pos_x, i32& pos_y, i32 reset_x, u32 w, u32 col, size_t s_end) {
|
||||
Font *f = ®ular;
|
||||
|
||||
String::const_iterator last = s.cbegin(), end = s.cend(), pos = std::find(last, end, u' '),
|
||||
halt = s_end > s.length() ? end : last + s_end;
|
||||
if (pos == end) { // Render the entire thing with hard break if we don't split at all
|
||||
String::const_iterator last_copy = last;
|
||||
i32 copy_x = pos_x, copy_y = pos_y;
|
||||
while (last != std::min(pos, halt)) {
|
||||
RenderGlyph(view_id, *last++, pos_x, pos_y, col);
|
||||
if (pos_x - reset_x > w) {
|
||||
pos_x = reset_x;
|
||||
pos_y -= f->face->size->metrics.height / 64;
|
||||
}
|
||||
if (last >= halt) {
|
||||
WalkString(view_id, last_copy, pos, copy_x, copy_y);
|
||||
return copy_x;
|
||||
};
|
||||
}
|
||||
}
|
||||
else while (last != end) { // Loop through all segments
|
||||
i32 copy_x = pos_x, old_x = pos_x, copy_y = pos_y;
|
||||
WalkString(view_id, last, pos, copy_x, copy_y);
|
||||
if (copy_x - reset_x > w) { // if walk exceeded max w
|
||||
copy_x = reset_x, copy_y = pos_y; // try walk again from leftmost of box, see if a soft break works; reset y from last walk
|
||||
WalkString(view_id, last, pos, copy_x, copy_y);
|
||||
if (copy_x - reset_x > w) { // soft break won't work, go back to old x and hard break
|
||||
pos_x = old_x;
|
||||
while (last != pos) {
|
||||
RenderGlyph(view_id, *last++, pos_x, pos_y, col);
|
||||
if (pos_x - reset_x > w) {
|
||||
pos_x = reset_x;
|
||||
pos_y -= f->face->size->metrics.height / 64;
|
||||
}
|
||||
if (last >= halt) return copy_x;
|
||||
}
|
||||
}
|
||||
else { // soft break and kill beginning space
|
||||
pos_x = reset_x;
|
||||
pos_y -= f->face->size->metrics.height / 64;
|
||||
last++;
|
||||
RenderString(view_id, last, std::min(pos, halt), pos_x, pos_y, col);
|
||||
if (last >= halt) return copy_x;
|
||||
}
|
||||
}
|
||||
else {
|
||||
RenderString(view_id, last, std::min(pos, halt), pos_x, pos_y, col);
|
||||
if (last >= halt) return copy_x;
|
||||
}
|
||||
|
||||
last = pos;
|
||||
if (pos != end)
|
||||
pos = std::find(std::next(pos), end, ' ');
|
||||
}
|
||||
return pos_x;
|
||||
}
|
||||
|
||||
void Composite(bgfx::FrameBufferHandle fb, bgfx::TextureHandle composite, bgfx::TextureHandle from, Blending mode, u16 w, u16 h, f32 proj[16], f32 transform[16]) {
|
||||
static f32 pack[4]{};
|
||||
|
|
|
@ -3,71 +3,71 @@
|
|||
#include <mutex>
|
||||
#include <thread>
|
||||
#include <Keishiki.h>
|
||||
//#include <glaze/glaze.hpp>
|
||||
#include <glaze/glaze.hpp>
|
||||
|
||||
#define STB_IMAGE_IMPLEMENTATION
|
||||
#include <stb_image.h>
|
||||
|
||||
//namespace glz {
|
||||
//template <>
|
||||
//struct meta<ImVec2> {
|
||||
// using T = ImVec2;
|
||||
// static constexpr auto value = array(&T::x, &T::y);
|
||||
//};
|
||||
//
|
||||
//template <>
|
||||
//struct meta<K::Uniform> {
|
||||
// using T = K::Uniform;
|
||||
// static constexpr auto value = object(&T::name,
|
||||
// &T::val,
|
||||
// // &T::connection, // todo need lookup
|
||||
// &T::status);
|
||||
//};
|
||||
//
|
||||
//template <>
|
||||
//struct meta<K::Sampler> {
|
||||
// using T = K::Sampler;
|
||||
// static constexpr auto value = object(&T::name);
|
||||
// // &T::resource, // todo need lookup
|
||||
// // &T::dims, // todo need lookup
|
||||
// // &T::frame); // todo need lookup
|
||||
//};
|
||||
//
|
||||
//template <>
|
||||
//struct meta<K::VisualTrack> {
|
||||
// using T = K::VisualTrack;
|
||||
// static constexpr auto value = object(&T::shader, &T::uniforms, &T::samplers);
|
||||
//};
|
||||
//
|
||||
//template <>
|
||||
//struct meta<K::Plugboard::Plugboard> {
|
||||
// using T = K::Plugboard::Plugboard;
|
||||
// static constexpr auto value = object(); // todo this one is actually so complicated
|
||||
//};
|
||||
//
|
||||
//template <>
|
||||
//struct meta<K::CompositionState> {
|
||||
// using T = K::CompositionState;
|
||||
// static constexpr auto value = object(&T::name,
|
||||
// &T::current_frame,
|
||||
// &T::frame_max,
|
||||
// &T::fps,
|
||||
// &T::width,
|
||||
// &T::height,
|
||||
// &T::layers,
|
||||
// &T::active,
|
||||
// &T::selected,
|
||||
// &T::disabled,
|
||||
// &T::plugboard);
|
||||
//};
|
||||
//
|
||||
//template <>
|
||||
//struct meta<K::ProjectState> {
|
||||
// using T = K::ProjectState;
|
||||
// static constexpr auto value = object(&T::compositions);
|
||||
//};
|
||||
//
|
||||
//}
|
||||
namespace glz {
|
||||
template <>
|
||||
struct meta<ImVec2> {
|
||||
using T = ImVec2;
|
||||
static constexpr auto value = array(&T::x, &T::y);
|
||||
};
|
||||
|
||||
template <>
|
||||
struct meta<K::Uniform> {
|
||||
using T = K::Uniform;
|
||||
static constexpr auto value = object(&T::name,
|
||||
&T::val,
|
||||
// &T::connection, // todo need lookup
|
||||
&T::status);
|
||||
};
|
||||
|
||||
template <>
|
||||
struct meta<K::Sampler> {
|
||||
using T = K::Sampler;
|
||||
static constexpr auto value = object(&T::name);
|
||||
// &T::resource, // todo need lookup
|
||||
// &T::dims, // todo need lookup
|
||||
// &T::frame); // todo need lookup
|
||||
};
|
||||
|
||||
template <>
|
||||
struct meta<K::VisualTrack> {
|
||||
using T = K::VisualTrack;
|
||||
static constexpr auto value = object(&T::shader, &T::uniforms, &T::samplers);
|
||||
};
|
||||
|
||||
template <>
|
||||
struct meta<K::Plugboard::Plugboard> {
|
||||
using T = K::Plugboard::Plugboard;
|
||||
static constexpr auto value = object(); // todo this one is actually so complicated
|
||||
};
|
||||
|
||||
template <>
|
||||
struct meta<K::CompositionState> {
|
||||
using T = K::CompositionState;
|
||||
static constexpr auto value = object(&T::name,
|
||||
&T::current_frame,
|
||||
&T::frame_max,
|
||||
&T::fps,
|
||||
&T::width,
|
||||
&T::height,
|
||||
&T::layers,
|
||||
&T::active,
|
||||
&T::selected,
|
||||
&T::disabled,
|
||||
&T::plugboard);
|
||||
};
|
||||
|
||||
template <>
|
||||
struct meta<K::ProjectState> {
|
||||
using T = K::ProjectState;
|
||||
static constexpr auto value = object(&T::compositions);
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
namespace K::Resource {
|
||||
void ReadProject() {
|
||||
|
@ -85,10 +85,10 @@ namespace K::Resource {
|
|||
return;
|
||||
|
||||
while (*filelist) {
|
||||
// auto ec = glz::read_file_json(app_state.project, *filelist, String{});
|
||||
// if (ec.ec != glz::error_code::none) {
|
||||
// Log(K_L_Error, "{}", ec.includer_error);
|
||||
// }
|
||||
auto ec = glz::read_file_json(app_state.project, *filelist, String{});
|
||||
if (ec.ec != glz::error_code::none) {
|
||||
Log(K_L_Error, "{}", ec.includer_error);
|
||||
}
|
||||
filelist++;
|
||||
}
|
||||
|
||||
|
@ -121,10 +121,10 @@ namespace K::Resource {
|
|||
return;
|
||||
|
||||
while (*filelist) {
|
||||
// auto ec = glz::write_file_json(app_state.project, *filelist, String{});
|
||||
// if (ec.ec != glz::error_code::none) {
|
||||
// Log(K_L_Error, "{}", ec.includer_error);
|
||||
// }
|
||||
auto ec = glz::write_file_json(app_state.project, *filelist, String{});
|
||||
if (ec.ec != glz::error_code::none) {
|
||||
Log(K_L_Error, "{}", ec.includer_error);
|
||||
}
|
||||
filelist++;
|
||||
}
|
||||
|
||||
|
@ -175,7 +175,7 @@ namespace K::Resource {
|
|||
std::shared_mutex resource_lock{};
|
||||
|
||||
std::filesystem::path ffmpeg_path = "ffmpeg";
|
||||
std::filesystem::path shaderc_path = "./ext/bgfx/cmake/bgfx/shaderc";
|
||||
std::filesystem::path shaderc_path = "/Users/lachrymal/Projects/Keishiki/build/Keishiki/ext/bgfx/cmake/bgfx/Debug/shaderc";
|
||||
const char *shaderc_temp_args;
|
||||
|
||||
Resource<Type::K_R_Still> *fallback_still;
|
||||
|
|
|
@ -2,8 +2,6 @@
|
|||
#include "Graphics.h"
|
||||
#include "VisualTrack.h"
|
||||
|
||||
#include <Actions.h>
|
||||
|
||||
#include <imgui.h>
|
||||
#include <imgui_internal.h>
|
||||
#include <misc/cpp/imgui_stdlib.h>
|
||||
|
@ -77,6 +75,53 @@ namespace K::UI {
|
|||
bgfx::setViewTransform(K::Graphics::K_VIEW_LOGO, view, proj);
|
||||
}
|
||||
|
||||
void AddTransformLayer(CompositionState& s, const String& name) {
|
||||
auto l = Layer{
|
||||
VisualTrack{},
|
||||
name,
|
||||
Graphics::K_V_AlphaOver,
|
||||
0UL,
|
||||
s.frame_max
|
||||
};
|
||||
l.track.AddUniform("u_resolution", ShaderGraph::ExpandVariant(ShaderGraph::T_XY), K_U_Exposed);
|
||||
l.track.uniforms[0].val = ShaderGraph::T_Map<ShaderGraph::T_XY>::type{static_cast<f32>(s.width), static_cast<f32>(s.height)};
|
||||
K::VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_opacity", ShaderGraph::ExpandVariant(ShaderGraph::T_Float), K_U_Exposed);
|
||||
l.track.uniforms[1].val = ShaderGraph::T_Map<ShaderGraph::T_Float>::type(1.0f);
|
||||
K::VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_rot", ShaderGraph::ExpandVariant(ShaderGraph::T_Float), K_U_Exposed);
|
||||
l.track.uniforms[2].val = ShaderGraph::T_Map<ShaderGraph::T_Float>::type(.0f);
|
||||
K::VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_scale", ShaderGraph::ExpandVariant(ShaderGraph::T_XY), K_U_Exposed);
|
||||
l.track.uniforms[3].val = ShaderGraph::T_Map<ShaderGraph::T_XY>::type{1.0f, 1.0f};
|
||||
K::VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.AddUniform("u_translate", ShaderGraph::ExpandVariant(ShaderGraph::T_XY), K_U_Exposed);
|
||||
l.track.uniforms[4].val = ShaderGraph::T_Map<ShaderGraph::T_XY>::type{.0f, .0f};
|
||||
K::VisualTrack::ExposeUniform(s, l.track.uniforms.back());
|
||||
|
||||
l.track.shader = "void main() {\n"
|
||||
"\tfloat angle = -u_rot * M_PI / 180.0f;\n"
|
||||
"\tvec2 uv = vec2(v_texcoord0.x, 1.0f - v_texcoord0.y) - .5f;\n"
|
||||
"\tuv = uv * u_resolution;\n"
|
||||
"\tuv = uv - u_translate;\n"
|
||||
"\tuv = vec2(cos(angle)*uv.x - sin(angle)*uv.y, sin(angle)*uv.x + cos(angle)*uv.y);\n"
|
||||
"\tuv = uv / s_texColor_dims;\n"
|
||||
"\tuv = uv / u_scale;\n"
|
||||
"\tuv = uv + .5f;\n\n"
|
||||
"\tvec4 tx = texture2D(s_texColor, uv);\n"
|
||||
"\tgl_FragColor = vec4(tx.rgb, tx.a * u_opacity);\n"
|
||||
"}\n";
|
||||
|
||||
l.track.AddSampler("s_texColor");
|
||||
|
||||
l.track.Compile();
|
||||
s.layers.push_back(std::move(l));
|
||||
}
|
||||
|
||||
void MainMenuBar() {
|
||||
if (ImGui::BeginMainMenuBar()) {
|
||||
if (ImGui::BeginMenu("File")) {
|
||||
|
@ -289,7 +334,6 @@ namespace K::UI {
|
|||
static bool do_bg = true, dragging = false;
|
||||
static f32 size = 1.0f, angle = 0;
|
||||
static ImVec2 pos{}, old = pos;
|
||||
static i32 ch = 0;
|
||||
|
||||
if (ImGui::Shortcut(ImGuiKey_Space))
|
||||
TogglePlay();
|
||||
|
@ -312,7 +356,7 @@ namespace K::UI {
|
|||
present = s.composite[result_index];
|
||||
|
||||
ImTextureID idx = ImGui::toId(present, 1, 0);
|
||||
if (idx != NULL) {
|
||||
if (idx != nullptr) {
|
||||
ImVec2 image_size = {static_cast<f32>(s.width) * size, static_cast<f32>(s.height) * size};
|
||||
|
||||
ImDrawList* draw_list = ImGui::GetWindowDrawList();
|
||||
|
@ -320,8 +364,8 @@ namespace K::UI {
|
|||
return ImVec2(v.x * cos_a - v.y * sin_a, v.x * sin_a + v.y * cos_a);
|
||||
};
|
||||
ImVec2 center = ImGui::GetCursorScreenPos() + ImGui::GetContentRegionAvail() * .5f + pos;
|
||||
f32 cos_a = std::cos(angle / 180.0f * std::numbers::pi);
|
||||
f32 sin_a = std::sin(angle / 180.0f * std::numbers::pi);
|
||||
f32 cos_a = std::cosf(angle / 180.0f * std::numbers::pi);
|
||||
f32 sin_a = std::sinf(angle / 180.0f * std::numbers::pi);
|
||||
ImVec2 quad[4] = {
|
||||
center + rot(ImVec2(-image_size.x * 0.5f, -image_size.y * 0.5f), cos_a, sin_a),
|
||||
center + rot(ImVec2(+image_size.x * 0.5f, -image_size.y * 0.5f), cos_a, sin_a),
|
||||
|
@ -336,7 +380,6 @@ namespace K::UI {
|
|||
};
|
||||
|
||||
draw_list->AddImageQuad(idx, quad[0], quad[1], quad[2], quad[3], uvs[0], uvs[1], uvs[2], uvs[3], IM_COL32_WHITE);
|
||||
draw_list->AddQuad(quad[0], quad[1], quad[2], quad[3], 0x22FFFFFF, 1.0f);
|
||||
}
|
||||
|
||||
/* ImGui::BeginDisabled(comp_save_called != nullptr);
|
||||
|
@ -376,18 +419,15 @@ namespace K::UI {
|
|||
ImGui::Text("%ux%u@%.1f", s.width, s.height, s.fps);
|
||||
ImGui::SameLine();
|
||||
f32 percentage = size * 100.0f;
|
||||
ImGui::SetNextItemWidth(100.0f);
|
||||
ImGui::SetNextItemWidth(110.0f);
|
||||
if (ImGui::InputFloat("View Scale", &percentage, 15.0f, 25.0f, "%.2f%%")) {
|
||||
size = std::max(.25f, percentage / 100.0f);
|
||||
}
|
||||
ImGui::SameLine();
|
||||
ImGui::SetNextItemWidth(35.0f);
|
||||
ImGui::SetNextItemWidth(50.0f);
|
||||
ImGui::DragFloat("View Angle", &angle, .05f, 0.0f, 0.0f, "%.1f");
|
||||
ImGui::SameLine();
|
||||
ImGui::SetNextItemWidth(90.0f);
|
||||
ImGui::Combo("Channels", &ch, "Combined\0Red\0Green\0Blue\0Alpha\0");
|
||||
ImGui::SameLine();
|
||||
ImGui::Checkbox("Alpha Grid", &do_bg);
|
||||
ImGui::Checkbox("Transparency Grid", &do_bg);
|
||||
}
|
||||
ImGui::EndChild();
|
||||
ImGui::PopStyleColor();
|
||||
|
@ -495,9 +535,9 @@ namespace K::UI {
|
|||
// Grid
|
||||
const f32 grid_inc = 20.0f;
|
||||
const f32 w = window->ContentRegionRect.GetWidth(), h = window->ContentRegionRect.GetHeight();
|
||||
for (f32 x = std::fmod(nodes_view_pos.x, grid_inc); x < w; x += grid_inc)
|
||||
for (f32 x = std::fmodf(nodes_view_pos.x, grid_inc); x < w; x += grid_inc)
|
||||
window->DrawList->AddLine(window_pos + ImVec2(x, 0.0f), window_pos + ImVec2(x, h), 0xFF222222, 1.0f);
|
||||
for (f32 y = std::fmod(nodes_view_pos.y, grid_inc); y < h; y += grid_inc)
|
||||
for (f32 y = std::fmodf(nodes_view_pos.y, grid_inc); y < h; y += grid_inc)
|
||||
window->DrawList->AddLine(window_pos + ImVec2(0.0f, y), window_pos + ImVec2(w, y), 0xFF222222, 1.0f);
|
||||
|
||||
// why are we re-getting positions on each frame?
|
||||
|
@ -2141,7 +2181,7 @@ namespace K::UI {
|
|||
|
||||
ImGui::DockSpaceOverViewport(0, ImGui::GetMainViewport(), ImGuiDockNodeFlags_PassthruCentralNode);
|
||||
|
||||
// ImGui::ShowDemoWindow();
|
||||
ImGui::ShowDemoWindow();
|
||||
MainMenuBar();
|
||||
|
||||
if (draw_assets) Assets();
|
||||
|
|
|
@ -1 +1 @@
|
|||
Subproject commit 615d2dcd5b6352aea50372745a05779e24ff8d31
|
||||
Subproject commit 4cc3410dce50cefce98d3cf3cf1bc8eca83b862a
|
|
@ -1 +1 @@
|
|||
Subproject commit 709e2d49f0d71d35203b0366a6d21b071059cb36
|
||||
Subproject commit 4ceffda6def0e57d70d8ea6aab8178be091fed37
|
|
@ -1 +1 @@
|
|||
Subproject commit 7e73566ce7bd3617cd4b14a2e3a19a2a30b524c7
|
||||
Subproject commit c98518351efd5a46f5d448e947e0b7242d197d07
|
|
@ -1 +1 @@
|
|||
Subproject commit 0ae7e607370cc66218ccfacf5de4db8a35424c2f
|
||||
Subproject commit ec378cecaf3cd656a9aa4bf237495d401521ae21
|
1
Keishiki/ext/glaze
Submodule
1
Keishiki/ext/glaze
Submodule
|
@ -0,0 +1 @@
|
|||
Subproject commit 951eccb69d7153206cc5487ca51256a24f518f6f
|
|
@ -1 +1 @@
|
|||
Subproject commit ee1deccc08c14ab1e6abcfa6aae11d915763cdb7
|
||||
Subproject commit 10a5a857f5b5cd6eae7f86461b939ec05e9235b2
|
|
@ -131,7 +131,7 @@ bool ImGui_Implbgfx_CreateFontsTexture()
|
|||
0, bgfx::copy(pixels, width * height * 4));
|
||||
|
||||
// Store our identifier
|
||||
io.Fonts->TexID = (ImTextureID)(intptr_t)g_FontTexture.idx;
|
||||
io.Fonts->TexID = (void*)(intptr_t)g_FontTexture.idx;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -1 +1 @@
|
|||
Subproject commit 419a8a0f5fcb77e1e7c19ab540441686bfe21bca
|
||||
Subproject commit f156599faefe316f7dd20fe6c783bf87c8bb6fd9
|
|
@ -1 +1 @@
|
|||
Subproject commit 55e9ad0867568e3dfb4d4c89efc3b9dde344060f
|
||||
Subproject commit 54df6ac3f500f4ec737c14636f7f908e6905081d
|
|
@ -1 +1 @@
|
|||
Subproject commit ddb95a8ae52d8015b5f22d67b2ca71e38faf435a
|
||||
Subproject commit 8ba8544709057644c7584a9b11158d28c71815ff
|
|
@ -1,9 +0,0 @@
|
|||
#include <Common.h>
|
||||
#include <Keishiki.h>
|
||||
|
||||
namespace K {
|
||||
struct Action {
|
||||
|
||||
};
|
||||
void AddTransformLayer(CompositionState& s, const String& name);
|
||||
}
|
|
@ -28,16 +28,16 @@ namespace K::Graphics {
|
|||
void DrawTextureStencilAlpha(u32 view_id, const bgfx::TextureHandle& tex, i32 pos_x, i32 pos_y, u32 w, u32 h);
|
||||
|
||||
// Text
|
||||
// void WalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y);
|
||||
// void RenderWalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y, u32 col);
|
||||
// void RenderGlyph(u32 view_id, Char c, i32 pos_x, i32 pos_y, u32 col);
|
||||
//
|
||||
// void WalkString(u32 view_id, const String& s, i32& pos_x, i32& pos_y);
|
||||
// void RenderString(u32 view_id, const String& s, i32 pos_x, i32 pos_y, u32 col);
|
||||
// void WalkString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32& pos_x, i32& pos_y);
|
||||
// void RenderString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32 pos_x, i32 pos_y, u32 col);
|
||||
//
|
||||
// i32 RenderSubstringBox(u32 view_id, const String& s, i32& pos_x, i32& pos_y, i32 reset_x, u32 w, u32 col, size_t s_end = String::npos);
|
||||
void WalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y);
|
||||
void RenderWalkGlyph(u32 view_id, Char c, i32& pos_x, i32& pos_y, u32 col);
|
||||
void RenderGlyph(u32 view_id, Char c, i32 pos_x, i32 pos_y, u32 col);
|
||||
|
||||
void WalkString(u32 view_id, const String& s, i32& pos_x, i32& pos_y);
|
||||
void RenderString(u32 view_id, const String& s, i32 pos_x, i32 pos_y, u32 col);
|
||||
void WalkString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32& pos_x, i32& pos_y);
|
||||
void RenderString(u32 view_id, String::const_iterator cbegin, String::const_iterator cend, i32 pos_x, i32 pos_y, u32 col);
|
||||
|
||||
i32 RenderSubstringBox(u32 view_id, const String& s, i32& pos_x, i32& pos_y, i32 reset_x, u32 w, u32 col, size_t s_end = String::npos);
|
||||
|
||||
enum Blending {
|
||||
K_V_AlphaOver = 0,
|
||||
|
|
|
@ -1,17 +1,17 @@
|
|||
import subprocess, os
|
||||
|
||||
#SHADERC = "..\\build\\Keishiki\\ext\\bgfx\\cmake\\bgfx\\Debug\\shaderc"
|
||||
# SHADERC = "/Users/lachrymal/Projects/Keishiki/build/Keishiki/ext/bgfx/cmake/bgfx/Debug/shaderc"
|
||||
SHADERC = "/home/lach/Projects/Keishiki/cmake-build-debug/Keishiki/ext/bgfx/cmake/bgfx/shaderc"
|
||||
# OUT = "..\\build\\Keishiki\\Debug\\shaders\\"
|
||||
# OUT = "/Users/lachrymal/Projects/Keishiki/Keishiki/runtime/shaders/"
|
||||
OUT = "/home/lach/Projects/Keishiki/cmake-build-debug/Keishiki/shaders/"
|
||||
I = "/home/lach/Projects/Keishiki/cmake-build-debug/Keishiki/"
|
||||
# I = "/Users/lachrymal/Projects/Keishiki/Keishiki/runtime/"
|
||||
SHADERC = "/Users/lachrymal/Projects/Keishiki/build/Keishiki/ext/bgfx/cmake/bgfx/Debug/shaderc"
|
||||
#SHADERC = "/home/lach/Projects/Keishiki/cmake-build-debug/Keishiki/ext/bgfx/cmake/bgfx/shaderc"
|
||||
#OUT = "..\\build\\Keishiki\\Debug\\shaders\\"
|
||||
OUT = "/Users/lachrymal/Projects/Keishiki/Keishiki/runtime/shaders/"
|
||||
#OUT = "/home/lach/Projects/Keishiki/cmake-build-debug/Keishiki/shaders/"
|
||||
#I = "/home/lach/Projects/Keishiki/cmake-build-debug/Keishiki/"
|
||||
I = "/Users/lachrymal/Projects/Keishiki/Keishiki/runtime/"
|
||||
|
||||
P = lambda location, platform, frag, vert: { 'location': location, 'platform': platform, 'frag': frag, 'vert': vert }
|
||||
plats = [
|
||||
P('glsl', 'linux', '440', '440'),
|
||||
P('glsl', 'windows', '140', '140'),
|
||||
# P('dx11', 'windows', 's_5_0', 's_5_0'),
|
||||
P('spirv', 'linux', 'spirv', 'spirv'),
|
||||
P('metal', 'osx', 'metal', 'metal')
|
||||
|
|
|
@ -3,11 +3,11 @@ $input v_texcoord0
|
|||
#include <bgfx_shader.sh>
|
||||
#include <shaderlib.sh>
|
||||
|
||||
uniform vec4 _f_hw;
|
||||
uniform vec4 __f_hw;
|
||||
|
||||
void main()
|
||||
{
|
||||
vec2 uv = vec2(v_texcoord0.x, (1.0f - v_texcoord0.y)) * _f_hw.xy / 20.0f;
|
||||
vec2 uv = vec2(v_texcoord0.x, (1.0f - v_texcoord0.y)) * __f_hw.xy / 20.0f;
|
||||
vec2 uvv = ceil(uv- floor(uv) - 0.5f);
|
||||
float b = 0.8f - mod((uvv.x + uvv.y), 2.0f) * 0.2;
|
||||
gl_FragColor = vec4(b, b, b, 1.0f);
|
||||
|
|
14
README.md
14
README.md
|
@ -1,8 +1,6 @@
|
|||
<img src="Keishiki.webp" alt="Logo" width="200"/>
|
||||
<img src="Keishiki.webp" alt="Logo" width="300"/>
|
||||
|
||||
# Keishiki: Real-Time Compositor-Sequencer Framework
|
||||

|
||||
|
||||
|
||||
## Libraries
|
||||
- [bgfx](https://github.com/bkaradzic/bgfx)
|
||||
|
@ -12,21 +10,13 @@
|
|||
- [Glaze](https://github.com/stephenberry/glaze)
|
||||
- [imgui_impl_bgfx](https://gist.github.com/pr0g/aff79b71bf9804ddb03f39ca7c0c3bbb)
|
||||
- [ImPlot](https://github.com/epezent/implot)
|
||||
- [SDL3](https://www.libsdl.org/)
|
||||
- [SDL2](https://www.libsdl.org/)
|
||||
- [stb](https://github.com/nothings/stb)
|
||||
- [SRELL](https://www.akenotsuki.com/misc/srell/en/)
|
||||
- [plf::colony](https://plflib.org/colony.htm)
|
||||
|
||||
Mostly using git submodules, please clone recursively.
|
||||
|
||||
## Runtime Dependency
|
||||
- [ffmpeg](https://ffmpeg.org/)
|
||||
- shaderc
|
||||
|
||||
Paths to runtime dependencies are currently hardcoded.
|
||||
|
||||
## Building
|
||||
Use `CMakeLists.txt` in the root directory. The default target is `Keishiki`.
|
||||
|
||||
## Inspired by
|
||||
- [Automaton](https://github.com/0b5vr/automaton)
|
||||
|
|
1
TODO.md
1
TODO.md
|
@ -37,7 +37,6 @@
|
|||
|
||||
# Later
|
||||
## Compositor
|
||||
- Investigate bgfx vulkan regression on 1109f3c5bf71f5e5c30fcaf6f899a25e3316adff
|
||||
- Simple 3D engine
|
||||
- Particles -- shoot for performance in https://github.com/CHCTW/DirectX12-Framework-
|
||||
- Flat sets and flat maps pending compiler support
|
||||
|
|
61
flake.lock
generated
61
flake.lock
generated
|
@ -1,61 +0,0 @@
|
|||
{
|
||||
"nodes": {
|
||||
"flake-utils": {
|
||||
"inputs": {
|
||||
"systems": "systems"
|
||||
},
|
||||
"locked": {
|
||||
"lastModified": 1726560853,
|
||||
"narHash": "sha256-X6rJYSESBVr3hBoH0WbKE5KvhPU5bloyZ2L4K60/fPQ=",
|
||||
"owner": "numtide",
|
||||
"repo": "flake-utils",
|
||||
"rev": "c1dfcf08411b08f6b8615f7d8971a2bfa81d5e8a",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
"owner": "numtide",
|
||||
"repo": "flake-utils",
|
||||
"type": "github"
|
||||
}
|
||||
},
|
||||
"nixpkgs": {
|
||||
"locked": {
|
||||
"lastModified": 1730200266,
|
||||
"narHash": "sha256-l253w0XMT8nWHGXuXqyiIC/bMvh1VRszGXgdpQlfhvU=",
|
||||
"owner": "NixOS",
|
||||
"repo": "nixpkgs",
|
||||
"rev": "807e9154dcb16384b1b765ebe9cd2bba2ac287fd",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
"owner": "NixOS",
|
||||
"ref": "nixos-unstable",
|
||||
"repo": "nixpkgs",
|
||||
"type": "github"
|
||||
}
|
||||
},
|
||||
"root": {
|
||||
"inputs": {
|
||||
"flake-utils": "flake-utils",
|
||||
"nixpkgs": "nixpkgs"
|
||||
}
|
||||
},
|
||||
"systems": {
|
||||
"locked": {
|
||||
"lastModified": 1681028828,
|
||||
"narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=",
|
||||
"owner": "nix-systems",
|
||||
"repo": "default",
|
||||
"rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e",
|
||||
"type": "github"
|
||||
},
|
||||
"original": {
|
||||
"owner": "nix-systems",
|
||||
"repo": "default",
|
||||
"type": "github"
|
||||
}
|
||||
}
|
||||
},
|
||||
"root": "root",
|
||||
"version": 7
|
||||
}
|
79
flake.nix
79
flake.nix
|
@ -1,79 +0,0 @@
|
|||
{
|
||||
inputs = {
|
||||
nixpkgs.url = "github:NixOS/nixpkgs/nixos-unstable";
|
||||
flake-utils.url = "github:numtide/flake-utils";
|
||||
};
|
||||
outputs = { self, nixpkgs, flake-utils, ... }: flake-utils.lib.eachDefaultSystem (system:
|
||||
let
|
||||
pkgs = import nixpkgs {
|
||||
inherit system;
|
||||
config.allowUnfree = true;
|
||||
};
|
||||
in
|
||||
{
|
||||
devShell = pkgs.mkShell rec {
|
||||
packages = with pkgs; [
|
||||
gcc
|
||||
libtool
|
||||
gnumake
|
||||
cmake
|
||||
gdb
|
||||
pkg-config
|
||||
jetbrains.clion
|
||||
python3
|
||||
|
||||
xorg.xorgproto
|
||||
xorg.libX11
|
||||
xorg.libX11.dev
|
||||
xorg.libxcb
|
||||
xorg.libxcb.dev
|
||||
xorg.libXext
|
||||
xorg.libXft
|
||||
xorg.libXinerama
|
||||
xorg.libXpm
|
||||
xorg.libXrandr
|
||||
xorg.libXrender
|
||||
xorg.libXau
|
||||
xorg.libXcursor
|
||||
xorg.libXi
|
||||
xorg.libXi.dev
|
||||
xorg.libXfixes
|
||||
xorg.libXxf86vm
|
||||
xorg.xinput
|
||||
xorg.libICE
|
||||
xorg.libXScrnSaver
|
||||
libdrm
|
||||
libGL
|
||||
libGL.dev
|
||||
libGLU
|
||||
libglvnd
|
||||
libglvnd.dev
|
||||
libxkbcommon
|
||||
mesa
|
||||
egl-wayland
|
||||
egl-wayland.dev
|
||||
wayland
|
||||
wayland-scanner
|
||||
alsa-lib
|
||||
audiofile
|
||||
dbus
|
||||
libdecor
|
||||
pipewire
|
||||
udev
|
||||
renderdoc
|
||||
vulkan-headers
|
||||
vulkan-helper
|
||||
vulkan-loader
|
||||
vulkan-tools
|
||||
vulkan-volk
|
||||
];
|
||||
shellHook = ''
|
||||
export LD_LIBRARY_PATH="$LD_LIBRARY_PATH:${
|
||||
with pkgs;
|
||||
lib.makeLibraryPath packages
|
||||
}"
|
||||
'';
|
||||
};
|
||||
}
|
||||
);
|
||||
}
|
Binary file not shown.
Before Width: | Height: | Size: 1 MiB |
Loading…
Add table
Reference in a new issue