summaryrefslogtreecommitdiffstatsci
diff options
context:
space:
mode:
authorJean-Philippe Bruyère <jp_bruyere@hotmail.com>2026-10-16 11:52:13 +0200
committerJean-Philippe Bruyère <jp_bruyere@hotmail.com>2026-10-16 11:52:13 +0200
commitd65ceda25ffe435114f0416d6bb1ad9164932907 (patch)
treecd7f802aa799abc12a1ede74a8baf93e1d30dde5
parent0ea75d9f9a84a9fdcb8375512165728aa2820ad7 (diff)
move pipeline,renderpass,dpy,sample count to surf
-rw-r--r--gunit_tests/drawTestBase.cpp2
-rw-r--r--gunit_tests/textDraw.cpp10
-rw-r--r--include/vkvg.h46
-rw-r--r--samples/VkvgTest.cpp2
-rw-r--r--src/svg/svg-parse.c4
-rw-r--r--src/vkvg_context.c22
-rw-r--r--src/vkvg_context_internal.c12
-rw-r--r--src/vkvg_device.c65
-rw-r--r--src/vkvg_device_internal.c328
-rw-r--r--src/vkvg_device_internal.h16
-rw-r--r--src/vkvg_fonts.c21
-rw-r--r--src/vkvg_surface.c31
-rw-r--r--src/vkvg_surface_internal.c378
-rw-r--r--src/vkvg_surface_internal.h12
-rw-r--r--tests/common/test.c4
-rw-r--r--tests/fonts/allfont.c6
-rw-r--r--tests/fonts/fontquery.c4
-rw-r--r--tests/text.c10
18 files changed, 488 insertions, 485 deletions
diff --git a/gunit_tests/drawTestBase.cpp b/gunit_tests/drawTestBase.cpp
index 9a92414..a4bdc20 100644
--- a/gunit_tests/drawTestBase.cpp
+++ b/gunit_tests/drawTestBase.cpp
@@ -23,6 +23,8 @@ DrawTestBase::DrawTestBase() {
vkvg_device_create_info_t info{};
info.samples = VK_SAMPLE_COUNT_4_BIT;
+ fs::path fontDir = fs::path(GTEST_DATA_ROOT) / "fonts";
+ info.fontsDirectories = fontDir.c_str();
dev = vkvg_device_create(&info);
}
diff --git a/gunit_tests/textDraw.cpp b/gunit_tests/textDraw.cpp
index 25b43a9..d543ed7 100644
--- a/gunit_tests/textDraw.cpp
+++ b/gunit_tests/textDraw.cpp
@@ -14,15 +14,15 @@ class TextDrawTest : public DrawTestBase {
}
};
TEST_F(TextDrawTest, References) {
- VkvgFont font = vkvg_font_create(dev, "sans", 12);
+ VkvgFont font = vkvg_font_create(surf, "sans", 12);
EXPECT_EQ(VKVG_STATUS_SUCCESS, vkvg_font_status(font));
vkvg_font_destroy(font);
- font = vkvg_font_create(dev, "Sans", 12);
+ font = vkvg_font_create(surf, "Sans", 12);
EXPECT_EQ(VKVG_STATUS_SUCCESS, vkvg_font_status(font));
vkvg_font_destroy(font);
- font = vkvg_font_create(dev, "noto sans jp", 12);
+ font = vkvg_font_create(surf, "noto sans jp", 12);
EXPECT_EQ(VKVG_STATUS_SUCCESS, vkvg_font_status(font));
vkvg_font_destroy(font);
@@ -55,7 +55,7 @@ TEST_F(TextDrawTest, ShowText) {
VkvgContext ctx = vkvg_create(surf);
vkvg_paint(ctx);
- VkvgFont font = vkvg_font_create(dev, "sans", 30);
+ VkvgFont font = vkvg_font_create(surf, "sans", 30);
vkvg_set_font(ctx, font);
vkvg_font_extents_t fe = {0};
vkvg_font_extents(ctx, &fe);
@@ -67,7 +67,7 @@ TEST_F(TextDrawTest, ShowText) {
vkvg_font_destroy(font);
- font = vkvg_font_create(dev, "noto sans jp", 30);
+ font = vkvg_font_create(surf, "noto sans jp", 30);
vkvg_set_font(ctx, font);
vkvg_move_to(ctx, 40, penY);
vkvg_show_text(ctx, "Galvanized by the quartz, The white rabbit just jumped on the red fox for the sake of the crows");
diff --git a/include/vkvg.h b/include/vkvg.h
index c457060..2378bbc 100644
--- a/include/vkvg.h
+++ b/include/vkvg.h
@@ -333,21 +333,21 @@ typedef struct _vkvg_font_t* VkvgFont;
* If fontconfig is enable, query strings with be parsed with fontconfig textural representation engine:
* <families>-<point sizes>:<name1>=<values1>:<name2>=<values2>...
*
- * @param dev Each font instance will be bound to a @ref VkvgDevice which holds the font cache.
+ * @param surf Each font instance will be bound to a @ref VkvgDevice which holds the font cache.
* @param queryString
* @param pointSize The font size in point unit, 1/72 of an inch.
* @return A new VkvgFont or null if an error occured.
*/
-vkvg_public VkvgFont vkvg_font_create (VkvgDevice dev, const char* queryString, float pointSize);
+vkvg_public VkvgFont vkvg_font_create (VkvgSurface surf, const char* queryString, float pointSize);
/**
* @brief Create a new @ref VkvgFont from the provided font file, face index and size.
- * @param dev VkvgDevice holding the font cache.
+ * @param surf VkvgDevice holding the font cache.
* @param fontFilePath a valid font file path.
* @param faceIndex Usually 0, except for variable fonts or font file with multiple faces.
* @param pointSize The font size in point unit, 1/72 of an inch.
* @return
*/
-vkvg_public VkvgFont vkvg_font_create_from_file (VkvgDevice dev, const char* fontFilePath, int faceIndex, float pointSize);
+vkvg_public VkvgFont vkvg_font_create_from_file (VkvgSurface surf, const char* fontFilePath, int faceIndex, float pointSize);
/**
* @brief Get underlying font face object pointer, if freetype is enable, the FT_Face will be returned.
* @param font a valid VkvgFont.
@@ -715,25 +715,6 @@ vkvg_public VkvgDevice vkvg_device_reference(VkvgDevice dev);
* @return The reference count on this device.
*/
vkvg_public uint32_t vkvg_device_get_reference_count(VkvgDevice dev);
-/**
- * @brief Set the screen dot per inch for this device.
- *
- * Set the current values for horizontal and vertical dot per inch of the screen for this device.
- * @param dev The vkvg device to set the dpy for.
- * @param hdpy Horizontal dot per inch.
- * @param vdpy Vertical dot per inch.
- */
-vkvg_public void vkvg_device_set_dpy(VkvgDevice dev, int hdpy, int vdpy);
-/**
- * @brief Get the current dpy values.
- *
- * Get the current values for horizontal and vertical dot per inch of the screen for this device.
- * The default values for horizontal and vertical dpy on device creation is 96.
- * @param dev The vkvg device to get the dpy configuration for.
- * @param hdpy The current horizontal dot per inch.
- * @param vdpy The current vertical dot per inch.
- */
-vkvg_public void vkvg_device_get_dpy(VkvgDevice dev, int* hdpy, int* vdpy);
/**
* @brief query required instance extensions for vkvg.
@@ -871,6 +852,25 @@ vkvg_public uint32_t vkvg_surface_get_width(VkvgSurface surf);
*/
vkvg_public uint32_t vkvg_surface_get_height(VkvgSurface surf);
/**
+ * @brief Set the screen dot per inch for this surface.
+ *
+ * Set the current values for horizontal and vertical dot per inch of the screen for this device.
+ * @param surf The vkvg surface to set the dpy for.
+ * @param hdpy Horizontal dot per inch.
+ * @param vdpy Vertical dot per inch.
+ */
+vkvg_public void vkvg_surface_set_dpy(VkvgSurface surf, int hdpy, int vdpy);
+/**
+ * @brief Get the current dpy values.
+ *
+ * Get the current values for horizontal and vertical dot per inch of the screen for this surface.
+ * The default values for horizontal and vertical dpy on device creation is 72.
+ * @param surf The vkvg surface to get the dpy configuration for.
+ * @param hdpy The current horizontal dot per inch.
+ * @param vdpy The current vertical dot per inch.
+ */
+vkvg_public void vkvg_surface_get_dpy(VkvgSurface surf, int* hdpy, int* vdpy);
+/**
* @brief Write surface content to a png file on disk.
* @param surf The surface to save on disk.
* @param path The png file path.
diff --git a/samples/VkvgTest.cpp b/samples/VkvgTest.cpp
index 6f5be46..24285d8 100644
--- a/samples/VkvgTest.cpp
+++ b/samples/VkvgTest.cpp
@@ -46,7 +46,7 @@ void VkvgTest::initTest(SampleApp* app) {
device = vkvg_device_create(&info);
surf = vkvg_surface_create(device, app->width, app->height);
- vkvg_device_set_dpy(device, 96, 96);
+ vkvg_surface_set_dpy(surf, 96, 96);
vkh_presenter_build_blit_cmd(app->renderer, vkvg_surface_get_vk_image(surf), app->width, app->height);
diff --git a/src/svg/svg-parse.c b/src/svg/svg-parse.c
index f4de1a0..3a56e5d 100644
--- a/src/svg/svg-parse.c
+++ b/src/svg/svg-parse.c
@@ -1415,7 +1415,7 @@ void parse_font_size(svg_context *const svg, SvgPresentationAttributes *attribs)
attribs->font_size_pt *= lop.number * 0.01f;
} else if (lop.units == svg_unit_px) {
int hdpy, vdpy;
- vkvg_device_get_dpy(svg->dev, &hdpy, &vdpy);
+ vkvg_surface_get_dpy(svg->surf, &hdpy, &vdpy);
attribs->font_size_pt = lop.number * (72.f / (float)vdpy);
} else if (lop.units == svg_unit_em) {
attribs->font_size_pt *= lop.number;
@@ -1570,7 +1570,7 @@ void process_element(svg_context *const svg, SvgPresentationAttributes *const at
if (attribs->font_family_len > 0) {
char fam[1024];
sprintf(fam, "%.*s", attribs->font_family_len, attribs->font_family);
- font = vkvg_font_create(svg->dev, fam, attribs->font_size_pt);
+ font = vkvg_font_create(svg->surf, fam, attribs->font_size_pt);
vkvg_set_font(svg->ctx, font);
vkvg_font_destroy(font);
}
diff --git a/src/vkvg_context.c b/src/vkvg_context.c
index bc0e646..e1c8fee 100644
--- a/src/vkvg_context.c
+++ b/src/vkvg_context.c
@@ -60,17 +60,17 @@ void _init_ctx(VkvgContext ctx) {
LOCK_SURFACE(ctx->pSurf)
if (ctx->pSurf->newSurf) {
- ctx->renderPassBeginInfo.renderPass = ctx->dev->renderPass_ClearAll;
+ ctx->renderPassBeginInfo.renderPass = ctx->pSurf->renderPass_ClearAll;
ctx->pSurf->newSurf = false;
} else {
- ctx->renderPassBeginInfo.renderPass = ctx->dev->renderPass_ClearStencil;
+ ctx->renderPassBeginInfo.renderPass = ctx->pSurf->renderPass_ClearStencil;
}
UNLOCK_SURFACE(ctx->pSurf);
vkvg_surface_reference(ctx->pSurf);
- ctx->renderPassBeginInfo.clearValueCount = ctx->dev->samples == VK_SAMPLE_COUNT_1_BIT ? 2 : 3;
+ ctx->renderPassBeginInfo.clearValueCount = ctx->pSurf->samples == VK_SAMPLE_COUNT_1_BIT ? 2 : 3;
#ifdef VKVG_ENABLE_VK_TIMELINE_SEMAPHORE
ctx->timelineStep = 0;
@@ -745,7 +745,7 @@ void _reset_clip(VkvgContext ctx) {
if (!ctx->cmdStarted) {
// if command buffer is not already started and in a renderpass, we use the renderpass
// with the loadop clear for stencil
- ctx->renderPassBeginInfo.renderPass = ctx->dev->renderPass_ClearStencil;
+ ctx->renderPassBeginInfo.renderPass = ctx->pSurf->renderPass_ClearStencil;
// force run of one renderpass (even empty) to perform clear load op
_start_cmd_for_render_pass(ctx);
return;
@@ -781,7 +781,7 @@ void vkvg_clear(VkvgContext ctx) {
_emit_draw_cmd_undrawn_vertices(ctx);
if (!ctx->cmdStarted) {
- ctx->renderPassBeginInfo.renderPass = ctx->dev->renderPass_ClearAll;
+ ctx->renderPassBeginInfo.renderPass = ctx->pSurf->renderPass_ClearAll;
_start_cmd_for_render_pass(ctx);
return;
}
@@ -806,9 +806,9 @@ void _clip_preserve(VkvgContext ctx) {
if (ctx->curFillRule == VKVG_FILL_RULE_EVEN_ODD) {
_poly_fill(ctx, NULL);
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipelineClipping);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipelineClipping);
} else {
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipelineClipping);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipelineClipping);
CmdSetStencilReference(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, STENCIL_FILL_BIT);
CmdSetStencilCompareMask(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, STENCIL_CLIP_BIT);
CmdSetStencilWriteMask(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, STENCIL_FILL_BIT);
@@ -1196,7 +1196,7 @@ void vkvg_select_font_face(VkvgContext ctx, const char* name) {
if (vkvg_status(ctx))
return;
RECORD(ctx, VKVG_CMD_SET_FONT_FACE, name);
- vkvg_set_font(ctx, vkvg_font_create(ctx->dev, name, 12));
+ vkvg_set_font(ctx, vkvg_font_create(ctx->pSurf, name, 12));
}
void vkvg_load_font_from_path(VkvgContext ctx, const char* path, const char* name) {
if (vkvg_status(ctx))
@@ -1359,7 +1359,7 @@ void vkvg_save(VkvgContext ctx) {
}
ctx->savedStencils = savedStencilsPtr;
VkhImage savStencil = vkh_image_ms_create(
- (VkhDevice)&ctx->dev->vkDev, dev->stencilFormat, dev->samples, ctx->pSurf->width, ctx->pSurf->height,
+ (VkhDevice)&ctx->dev->vkDev, dev->stencilFormat, ctx->pSurf->samples, ctx->pSurf->width, ctx->pSurf->height,
VKH_MEMORY_USAGE_GPU_ONLY, VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT);
ctx->savedStencils[curSaveStencil - 1] = savStencil;
@@ -1403,7 +1403,7 @@ void vkvg_save(VkvgContext ctx) {
vkh_cmd_label_start(ctx->cmd, "save rp", DBG_LAB_COLOR_SAV);
#endif
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipelineClipping);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipelineClipping);
CmdSetStencilReference(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, STENCIL_CLIP_BIT | curSaveBit);
CmdSetStencilCompareMask(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, STENCIL_CLIP_BIT);
@@ -1467,7 +1467,7 @@ void vkvg_restore(VkvgContext ctx) {
vkh_cmd_label_start(ctx->cmd, "restore rp", DBG_LAB_COLOR_SAV);
#endif
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipelineClipping);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipelineClipping);
CmdSetStencilReference(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, STENCIL_CLIP_BIT | curSaveBit);
CmdSetStencilCompareMask(ctx->cmd, VK_STENCIL_FRONT_AND_BACK, curSaveBit);
diff --git a/src/vkvg_context_internal.c b/src/vkvg_context_internal.c
index a9fc268..6f10f76 100644
--- a/src/vkvg_context_internal.c
+++ b/src/vkvg_context_internal.c
@@ -530,7 +530,7 @@ void _end_render_pass(VkvgContext ctx) {
#if defined(DEBUG) && defined(VKVG_DBG_UTILS)
vkh_cmd_label_end(ctx->cmd);
#endif
- ctx->renderPassBeginInfo.renderPass = ctx->dev->renderPass;
+ ctx->renderPassBeginInfo.renderPass = ctx->pSurf->renderPass;
}
void _check_vao_size(VkvgContext ctx) {
@@ -607,16 +607,16 @@ void _flush_cmd_buff(VkvgContext ctx) {
void _bind_draw_pipeline(VkvgContext ctx) {
switch (ctx->curOperator) {
case VKVG_OPERATOR_OVER:
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipe_OVER);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipe_OVER);
break;
case VKVG_OPERATOR_CLEAR:
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipe_CLEAR);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipe_CLEAR);
break;
case VKVG_OPERATOR_DIFFERENCE:
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipe_SUB);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipe_SUB);
break;
default:
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipe_OVER);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipe_OVER);
break;
}
}
@@ -1602,7 +1602,7 @@ void _poly_fill(VkvgContext ctx, vec4* bounds) {
_ensure_renderpass_is_started(ctx);
}
- CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->dev->pipelinePolyFill);
+ CmdBindPipeline(ctx->cmd, VK_PIPELINE_BIND_POINT_GRAPHICS, ctx->pSurf->pipelinePolyFill);
Vertex v = {{0}, ctx->curColor, {0, 0, -1}};
uint32_t ptrPath = 0;
diff --git a/src/vkvg_device.c b/src/vkvg_device.c
index 6b805e4..ea47024 100644
--- a/src/vkvg_device.c
+++ b/src/vkvg_device.c
@@ -68,13 +68,6 @@ void _device_init(VkvgDevice dev, const vkvg_device_create_info_t* info) {
dev->vkDev = info->vkdev;
dev->phy = info->phy;
dev->instance = info->inst;
- dev->hdpi = 72;
- dev->vdpi = 72;
- dev->samples = info->samples;
- if (dev->samples == VK_SAMPLE_COUNT_1_BIT)
- dev->deferredResolve = false;
- else
- dev->deferredResolve = info->deferredResolve;
dev->cachedContextMaxCount = VKVG_MAX_CACHED_CONTEXT_COUNT;
@@ -114,23 +107,7 @@ void _device_init(VkvgDevice dev, const vkvg_device_create_info_t* info) {
//_device_create_pipeline_cache(dev);
_fonts_cache_create(dev, info->fontsDirectories);
-
- if (dev->deferredResolve || dev->samples == VK_SAMPLE_COUNT_1_BIT) {
- dev->renderPass =
- _device_createRenderPassNoResolve(dev, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_LOAD);
- dev->renderPass_ClearStencil =
- _device_createRenderPassNoResolve(dev, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_CLEAR);
- dev->renderPass_ClearAll =
- _device_createRenderPassNoResolve(dev, VK_ATTACHMENT_LOAD_OP_CLEAR, VK_ATTACHMENT_LOAD_OP_CLEAR);
- } else {
- dev->renderPass = _device_createRenderPassMS(dev, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_LOAD);
- dev->renderPass_ClearStencil =
- _device_createRenderPassMS(dev, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_CLEAR);
- dev->renderPass_ClearAll =
- _device_createRenderPassMS(dev, VK_ATTACHMENT_LOAD_OP_CLEAR, VK_ATTACHMENT_LOAD_OP_CLEAR);
- }
_device_createDescriptorSetLayout(dev);
- _device_setupPipelines(dev);
_device_create_empty_texture(dev, format, dev->supportedTiling);
@@ -148,24 +125,12 @@ void _device_init(VkvgDevice dev, const vkvg_device_create_info_t* info) {
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_COMMAND_POOL, (uint64_t)dev->cmdPool, "Device Cmd Pool");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_COMMAND_BUFFER, (uint64_t)dev->cmd, "Device Cmd Buff");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_FENCE, (uint64_t)dev->fence, "Device Fence");
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_RENDER_PASS, (uint64_t)dev->renderPass, "RP load img/stencil");
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_RENDER_PASS, (uint64_t)dev->renderPass_ClearStencil,
- "RP clear stencil");
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_RENDER_PASS, (uint64_t)dev->renderPass_ClearAll, "RP clear all");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT, (uint64_t)dev->dslSrc, "DSLayout SOURCE");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT, (uint64_t)dev->dslFont, "DSLayout FONT");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT, (uint64_t)dev->dslGrad, "DSLayout GRADIENT");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE_LAYOUT, (uint64_t)dev->pipelineLayout, "PLLayout dev");
-#ifndef __APPLE__
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)dev->pipelinePolyFill, "PL Poly fill");
-#endif
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)dev->pipelineClipping, "PL Clipping");
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)dev->pipe_OVER, "PL draw Over");
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)dev->pipe_SUB, "PL draw Substract");
- vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)dev->pipe_CLEAR, "PL draw Clear");
-
vkh_image_set_name(dev->emptyImg, "empty IMG");
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_IMAGE_VIEW, (uint64_t)vkh_image_get_view(dev->emptyImg),
"empty IMG VIEW");
@@ -438,25 +403,9 @@ void vkvg_device_destroy(VkvgDevice dev) {
vkDestroyDescriptorSetLayout(dev->vkDev, dev->dslGrad, NULL);
vkDestroyDescriptorSetLayout(dev->vkDev, dev->dslFont, NULL);
vkDestroyDescriptorSetLayout(dev->vkDev, dev->dslSrc, NULL);
-#ifndef __APPLE__
- vkDestroyPipeline(dev->vkDev, dev->pipelinePolyFill, NULL);
-#endif
- vkDestroyPipeline(dev->vkDev, dev->pipelineClipping, NULL);
-
- vkDestroyPipeline(dev->vkDev, dev->pipe_OVER, NULL);
- vkDestroyPipeline(dev->vkDev, dev->pipe_SUB, NULL);
- vkDestroyPipeline(dev->vkDev, dev->pipe_CLEAR, NULL);
-
-#ifdef VKVG_WIRED_DEBUG
- vkDestroyPipeline(dev->vkDev, dev->pipelineWired, NULL);
- vkDestroyPipeline(dev->vkDev, dev->pipelineLineList, NULL);
-#endif
vkDestroyPipelineLayout(dev->vkDev, dev->pipelineLayout, NULL);
vkDestroyPipelineCache(dev->vkDev, dev->pipelineCache, NULL);
- vkDestroyRenderPass(dev->vkDev, dev->renderPass, NULL);
- vkDestroyRenderPass(dev->vkDev, dev->renderPass_ClearStencil, NULL);
- vkDestroyRenderPass(dev->vkDev, dev->renderPass_ClearAll, NULL);
vkWaitForFences(dev->vkDev, 1, &dev->fence, VK_TRUE, UINT64_MAX);
vkDestroyFence(dev->vkDev, dev->fence, NULL);
@@ -497,21 +446,7 @@ VkvgDevice vkvg_device_reference(VkvgDevice dev) {
return dev;
}
uint32_t vkvg_device_get_reference_count(VkvgDevice dev) { return vkvg_device_status(dev) ? 0 : dev->references; }
-// TODO dpy reorganisation
-void vkvg_device_set_dpy(VkvgDevice dev, int hdpy, int vdpy) {
- if (vkvg_device_status(dev))
- return;
- dev->hdpi = hdpy;
- dev->vdpi = vdpy;
- // TODO: reset font cache
-}
-void vkvg_device_get_dpy(VkvgDevice dev, int* hdpy, int* vdpy) {
- if (vkvg_device_status(dev))
- return;
- *hdpy = dev->hdpi;
- *vdpy = dev->vdpi;
-}
#if VKVG_DBG_STATS
vkvg_debug_stats_t vkvg_device_get_stats(VkvgDevice dev) {
return vkvg_device_status(dev) ? (vkvg_debug_stats_t){0} : dev->debug_stats;
diff --git a/src/vkvg_device_internal.c b/src/vkvg_device_internal.c
index 497e911..c3e61bc 100644
--- a/src/vkvg_device_internal.c
+++ b/src/vkvg_device_internal.c
@@ -28,7 +28,6 @@
#include "vkvg_device_internal.h"
#include "vkvg_context_internal.h"
-#include "shaders.h"
uint32_t vkvg_log_level = VKVG_LOG_DEBUG;
#ifdef VKVG_WIRED_DEBUG
@@ -73,333 +72,6 @@ void _device_create_pipeline_cache(VkvgDevice dev) {
VK_CHECK_RESULT(vkCreatePipelineCache(dev->vkDev, &pipelineCacheCreateInfo, NULL, &dev->pipelineCache));
}
-VkRenderPass _device_createRenderPassNoResolve(VkvgDevice dev, VkAttachmentLoadOp loadOp,
- VkAttachmentLoadOp stencilLoadOp) {
- VkAttachmentDescription attColor = {.format = FB_COLOR_FORMAT,
- .samples = dev->samples,
- .loadOp = loadOp,
- .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
- .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
- .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
- .initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
- .finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
- VkAttachmentDescription attDS = {.format = dev->stencilFormat,
- .samples = dev->samples,
- .loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
- .storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
- .stencilLoadOp = stencilLoadOp,
- .stencilStoreOp = VK_ATTACHMENT_STORE_OP_STORE,
- .initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
- .finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
-
- VkAttachmentDescription attachments[] = {attColor, attDS};
- VkAttachmentReference colorRef = {0, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
- VkAttachmentReference dsRef = {1, VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
-
- VkSubpassDescription subpassDescription = {.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS,
- .colorAttachmentCount = 1,
- .pColorAttachments = &colorRef,
- .pDepthStencilAttachment = &dsRef};
-
- VkSubpassDependency dependencies[] = {
- {VK_SUBPASS_EXTERNAL, 0, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
- VK_ACCESS_MEMORY_READ_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,
- VK_DEPENDENCY_BY_REGION_BIT},
- {0, VK_SUBPASS_EXTERNAL, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT,
- VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, VK_ACCESS_MEMORY_READ_BIT,
- VK_DEPENDENCY_BY_REGION_BIT},
- };
-
- VkRenderPassCreateInfo renderPassInfo = {.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
- .attachmentCount = 2,
- .pAttachments = attachments,
- .subpassCount = 1,
- .pSubpasses = &subpassDescription,
- .dependencyCount = 2,
- .pDependencies = dependencies};
- VkRenderPass rp;
- VK_CHECK_RESULT(vkCreateRenderPass(dev->vkDev, &renderPassInfo, NULL, &rp));
- return rp;
-}
-VkRenderPass _device_createRenderPassMS(VkvgDevice dev, VkAttachmentLoadOp loadOp, VkAttachmentLoadOp stencilLoadOp) {
- VkAttachmentDescription attColor = {.format = FB_COLOR_FORMAT,
- .samples = dev->samples,
- .loadOp = loadOp,
- .storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
- .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
- .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
- .initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
- .finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
- VkAttachmentDescription attColorResolve = {.format = FB_COLOR_FORMAT,
- .samples = VK_SAMPLE_COUNT_1_BIT,
- .loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
- .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
- .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
- .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
- .initialLayout = VK_IMAGE_LAYOUT_UNDEFINED,
- .finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
- VkAttachmentDescription attDS = {.format = dev->stencilFormat,
- .samples = dev->samples,
- .loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
- .storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
- .stencilLoadOp = stencilLoadOp,
- .stencilStoreOp = VK_ATTACHMENT_STORE_OP_STORE,
- .initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
- .finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
-
- VkAttachmentDescription attachments[] = {attColorResolve, attDS, attColor};
- VkAttachmentReference resolveRef = {0, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
- VkAttachmentReference dsRef = {1, VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
- VkAttachmentReference colorRef = {2, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
-
- VkSubpassDescription subpassDescription = {.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS,
- .colorAttachmentCount = 1,
- .pColorAttachments = &colorRef,
- .pResolveAttachments = &resolveRef,
- .pDepthStencilAttachment = &dsRef};
-
- VkSubpassDependency dependencies[] = {
- {VK_SUBPASS_EXTERNAL, 0, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
- VK_ACCESS_MEMORY_READ_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,
- VK_DEPENDENCY_BY_REGION_BIT},
- {0, VK_SUBPASS_EXTERNAL, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT,
- VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, VK_ACCESS_MEMORY_READ_BIT,
- VK_DEPENDENCY_BY_REGION_BIT},
- };
-
- VkRenderPassCreateInfo renderPassInfo = {.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
- .attachmentCount = 3,
- .pAttachments = attachments,
- .subpassCount = 1,
- .pSubpasses = &subpassDescription,
- .dependencyCount = 2,
- .pDependencies = dependencies};
- VkRenderPass rp;
- VK_CHECK_RESULT(vkCreateRenderPass(dev->vkDev, &renderPassInfo, NULL, &rp));
- return rp;
-}
-
-void _device_setupPipelines(VkvgDevice dev) {
- VkGraphicsPipelineCreateInfo pipelineCreateInfo = {.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO,
- .renderPass = dev->renderPass};
-
- VkPipelineInputAssemblyStateCreateInfo inputAssemblyState = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
- .topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_FAN};
-
- VkPipelineRasterizationStateCreateInfo rasterizationState = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
- .polygonMode = VK_POLYGON_MODE_FILL,
- .cullMode = VK_CULL_MODE_NONE,
- .frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE,
- .depthClampEnable = VK_FALSE,
- .rasterizerDiscardEnable = VK_FALSE,
- .depthBiasEnable = VK_FALSE,
- .lineWidth = 1.0f};
-
- VkPipelineColorBlendAttachmentState blendAttachmentState = {
- .colorWriteMask = 0x0,
- .blendEnable = VK_TRUE,
-#ifdef VKVG_PREMULT_ALPHA
- .srcColorBlendFactor = VK_BLEND_FACTOR_ONE,
- .dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA,
- .colorBlendOp = VK_BLEND_OP_ADD,
- .srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE,
- .dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA,
- .alphaBlendOp = VK_BLEND_OP_ADD,
-#else
- .srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA,
- .dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA,
- .colorBlendOp = VK_BLEND_OP_ADD,
- .srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE,
- .dstAlphaBlendFactor = VK_BLEND_FACTOR_ZERO,
- .alphaBlendOp = VK_BLEND_OP_ADD,
-#endif
- };
-
- VkPipelineColorBlendStateCreateInfo colorBlendState = {.sType =
- VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO,
- .attachmentCount = 1,
- .pAttachments = &blendAttachmentState};
-
- /*failOp,passOp,depthFailOp,compareOp, compareMask, writeMask, reference;*/
- VkStencilOpState polyFillOpState = {VK_STENCIL_OP_KEEP,
- VK_STENCIL_OP_INVERT,
- VK_STENCIL_OP_KEEP,
- VK_COMPARE_OP_EQUAL,
- STENCIL_CLIP_BIT,
- STENCIL_FILL_BIT,
- 0};
- VkStencilOpState clipingOpState = {VK_STENCIL_OP_ZERO,
- VK_STENCIL_OP_REPLACE,
- VK_STENCIL_OP_KEEP,
- VK_COMPARE_OP_EQUAL,
- STENCIL_FILL_BIT,
- STENCIL_ALL_BIT,
- 0x2};
- VkStencilOpState stencilOpState = {VK_STENCIL_OP_KEEP,
- VK_STENCIL_OP_ZERO,
- VK_STENCIL_OP_KEEP,
- VK_COMPARE_OP_EQUAL,
- STENCIL_FILL_BIT,
- STENCIL_FILL_BIT,
- 0x1};
-
- VkPipelineDepthStencilStateCreateInfo dsStateCreateInfo = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
- .depthTestEnable = VK_FALSE,
- .depthWriteEnable = VK_FALSE,
- .depthCompareOp = VK_COMPARE_OP_ALWAYS,
- .stencilTestEnable = VK_TRUE,
- .front = polyFillOpState,
- .back = polyFillOpState};
-
- VkDynamicState dynamicStateEnables[] = {
- VK_DYNAMIC_STATE_VIEWPORT,
- VK_DYNAMIC_STATE_SCISSOR,
- VK_DYNAMIC_STATE_STENCIL_COMPARE_MASK,
- VK_DYNAMIC_STATE_STENCIL_REFERENCE,
- VK_DYNAMIC_STATE_STENCIL_WRITE_MASK,
- };
- VkPipelineDynamicStateCreateInfo dynamicState = {.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO,
- .dynamicStateCount = 2,
- .pDynamicStates = dynamicStateEnables};
-
- VkPipelineViewportStateCreateInfo viewportState = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO, .viewportCount = 1, .scissorCount = 1};
-
- VkPipelineMultisampleStateCreateInfo multisampleState = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, .rasterizationSamples = dev->samples};
- /*if (dev->samples != VK_SAMPLE_COUNT_1_BIT){
- multisampleState.sampleShadingEnable = VK_TRUE;
- multisampleState.minSampleShading = 0.5f;
- }*/
- VkVertexInputBindingDescription vertexInputBinding = {
- .binding = 0, .stride = sizeof(Vertex), .inputRate = VK_VERTEX_INPUT_RATE_VERTEX};
-
- VkVertexInputAttributeDescription vertexInputAttributs[3] = {{0, 0, VK_FORMAT_R32G32_SFLOAT, 0},
- {1, 0, VK_FORMAT_R8G8B8A8_UNORM, 8},
- {2, 0, VK_FORMAT_R32G32B32_SFLOAT, 12}};
-
- VkPipelineVertexInputStateCreateInfo vertexInputState = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
- .vertexBindingDescriptionCount = 1,
- .pVertexBindingDescriptions = &vertexInputBinding,
- .vertexAttributeDescriptionCount = 3,
- .pVertexAttributeDescriptions = vertexInputAttributs};
-#ifdef VKVG_WIRED_DEBUG
- VkShaderModule modVert, modFrag, modFragWired;
-#else
- VkShaderModule modVert, modFrag;
-#endif
- VkShaderModuleCreateInfo createInfo = {.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO,
- .pCode = (uint32_t*)vkvg_main_vert_spv,
- .codeSize = vkvg_main_vert_spv_len};
- VK_CHECK_RESULT(vkCreateShaderModule(dev->vkDev, &createInfo, NULL, &modVert));
-#if defined(VKVG_LCD_FONT_FILTER) && defined(FT_CONFIG_OPTION_SUBPIXEL_RENDERING)
- createInfo.pCode = (uint32_t*)vkvg_main_lcd_frag_spv;
- createInfo.codeSize = vkvg_main_lcd_frag_spv_len;
-#else
- createInfo.pCode = (uint32_t*)vkvg_main_frag_spv;
- createInfo.codeSize = vkvg_main_frag_spv_len;
-#endif
- VK_CHECK_RESULT(vkCreateShaderModule(dev->vkDev, &createInfo, NULL, &modFrag));
-
- VkPipelineShaderStageCreateInfo vertStage = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
- .stage = VK_SHADER_STAGE_VERTEX_BIT,
- .module = modVert,
- .pName = "main",
- };
- VkPipelineShaderStageCreateInfo fragStage = {
- .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
- .stage = VK_SHADER_STAGE_FRAGMENT_BIT,
- .module = modFrag,
- .pName = "main",
- };
-
- // Use specialization constants to pass number of samples to the shader (used for MSAA resolve)
- /*VkSpecializationMapEntry specializationEntry = {
- .constantID = 0,
- .offset = 0,
- .size = sizeof(uint32_t)};
- uint32_t specializationData = VKVG_SAMPLES;
- VkSpecializationInfo specializationInfo = {
- .mapEntryCount = 1,
- .pMapEntries = &specializationEntry,
- .dataSize = sizeof(specializationData),
- .pData = &specializationData};*/
-
- VkPipelineShaderStageCreateInfo shaderStages[] = {vertStage, fragStage};
-
- pipelineCreateInfo.stageCount = 1;
- pipelineCreateInfo.pStages = shaderStages;
- pipelineCreateInfo.pVertexInputState = &vertexInputState;
- pipelineCreateInfo.pInputAssemblyState = &inputAssemblyState;
- pipelineCreateInfo.pViewportState = &viewportState;
- pipelineCreateInfo.pRasterizationState = &rasterizationState;
- pipelineCreateInfo.pMultisampleState = &multisampleState;
- pipelineCreateInfo.pColorBlendState = &colorBlendState;
- pipelineCreateInfo.pDepthStencilState = &dsStateCreateInfo;
- pipelineCreateInfo.pDynamicState = &dynamicState;
- pipelineCreateInfo.layout = dev->pipelineLayout;
-
-#ifndef __APPLE__
- VK_CHECK_RESULT(vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL,
- &dev->pipelinePolyFill));
-#endif
-
- inputAssemblyState.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
- dsStateCreateInfo.back = dsStateCreateInfo.front = clipingOpState;
- dynamicState.dynamicStateCount = 5;
- VK_CHECK_RESULT(vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL,
- &dev->pipelineClipping));
-
- dsStateCreateInfo.back = dsStateCreateInfo.front = stencilOpState;
- blendAttachmentState.colorWriteMask = 0xf;
- dynamicState.dynamicStateCount = 3;
- pipelineCreateInfo.stageCount = 2;
- VK_CHECK_RESULT(
- vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &dev->pipe_OVER));
-
- blendAttachmentState.alphaBlendOp = blendAttachmentState.colorBlendOp = VK_BLEND_OP_SUBTRACT;
- VK_CHECK_RESULT(
- vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &dev->pipe_SUB));
-
- colorBlendState.logicOpEnable = VK_TRUE;
- blendAttachmentState.blendEnable = VK_FALSE;
- colorBlendState.logicOp = VK_LOGIC_OP_CLEAR;
- VK_CHECK_RESULT(
- vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &dev->pipe_CLEAR));
-
-#ifdef VKVG_WIRED_DEBUG
- colorBlendState.logicOpEnable = VK_FALSE;
- blendAttachmentState.blendEnable = VK_TRUE;
- colorBlendState.logicOp = VK_LOGIC_OP_CLEAR;
-
- createInfo.pCode = (uint32_t*)wired_frag_spv;
-
- createInfo.codeSize = wired_frag_spv_len;
- VK_CHECK_RESULT(vkCreateShaderModule(dev->vkDev, &createInfo, NULL, &modFragWired));
-
- shaderStages[1].module = modFragWired;
-
- rasterizationState.polygonMode = VK_POLYGON_MODE_LINE;
- VK_CHECK_RESULT(vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL,
- &dev->pipelineLineList));
-
- inputAssemblyState.topology = VK_PRIMITIVE_TOPOLOGY_POINT_LIST;
- rasterizationState.polygonMode = VK_POLYGON_MODE_FILL;
- VK_CHECK_RESULT(
- vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &dev->pipelineWired));
-
- vkDestroyShaderModule(dev->vkDev, modFragWired, NULL);
-#endif
-
- vkDestroyShaderModule(dev->vkDev, modVert, NULL);
- vkDestroyShaderModule(dev->vkDev, modFrag, NULL);
-}
-
void _device_createDescriptorSetLayout(VkvgDevice dev) {
VkDescriptorSetLayoutBinding dsLayoutBinding = {0, VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER, 1,
diff --git a/src/vkvg_device_internal.h b/src/vkvg_device_internal.h
index a436cd9..a455d42 100644
--- a/src/vkvg_device_internal.h
+++ b/src/vkvg_device_internal.h
@@ -79,21 +79,11 @@ typedef struct _vkvg_device_t {
bool threadAware; /**< if true, mutex is created and guard device queue and caches access */
VkhQueue gQueue; /**< Vulkan Queue with Graphic flag */
- VkRenderPass renderPass; /**< Vulkan render pass, common for all surfaces */
- VkRenderPass renderPass_ClearStencil; /**< Vulkan render pass for first draw with context, stencil has to be cleared */
- VkRenderPass renderPass_ClearAll; /**< Vulkan render pass for new surface, clear all attacments*/
-
uint32_t references; /**< Reference count, prevent destroying device if still in use */
VkCommandPool cmdPool; /**< Global command pool for processing on surfaces without context */
VkCommandBuffer cmd; /**< Global command buffer */
VkFence fence; /**< this fence is kept signaled when idle, wait and reset are called before each recording. */
- VkPipeline pipe_OVER; /**< default operator */
- VkPipeline pipe_SUB;
- VkPipeline pipe_CLEAR; /**< clear operator */
-
- VkPipeline pipelinePolyFill; /**< even-odd polygon filling first step */
- VkPipeline pipelineClipping; /**< draw on stencil to update clipping regions */
VkPipelineCache pipelineCache; /**< speed up startup by caching configured pipelines on disk */
VkPipelineLayout pipelineLayout; /**< layout common to all pipelines */
@@ -101,13 +91,9 @@ typedef struct _vkvg_device_t {
VkDescriptorSetLayout dslSrc; /**< context source surface descriptors layout */
VkDescriptorSetLayout dslGrad; /**< context gradient descriptors layout */
- int hdpi, /**< only used for FreeType fonts and svg loading */
- vdpi;
-
VkhDevice vkhDev; /**< old VkhDev created during vulkan context creation by @ref vkvg_device_create. */
- VkhImage emptyImg; /**< prevent unbound descriptor to trigger Validation error 61 */
- VkSampleCountFlags samples; /**< samples count common to all surfaces */
+ VkhImage emptyImg; /**< prevent unbound descriptor to trigger Validation error 61 */
bool deferredResolve; /**< if true, resolve only on context destruction and set as source */
_font_cache_t* fontCache; /**< Store everything relative to common font caching system */
diff --git a/src/vkvg_fonts.c b/src/vkvg_fonts.c
index 7d7c356..017dbe6 100644
--- a/src/vkvg_fonts.c
+++ b/src/vkvg_fonts.c
@@ -4,6 +4,7 @@
#include "vkvg_fonts.h"
#include "vkvg_context_internal.h"
#include "vkvg_device_internal.h"
+#include "vkvg_surface_internal.h"
#include "vkh.h"
@@ -712,6 +713,8 @@ bool try_get_font_size (FontFace face, uint32_t pt26_6, signed long* coords, Vkv
for (int i = 0; i < face->sizes.count; ++i) {
VkvgFont f = face->sizes.elements[i];
if (f->charSize == pt26_6) {
+ if (!coords)
+ return true;
for (int axe = 0; axe < face->numAxis; ++axe) {
if (f->coords[axe] != coords[axe])
return false;
@@ -994,7 +997,7 @@ void* vkvg_font_get_face(VkvgFont font) {
#endif
}
-VkvgFont _create_font_from_face (VkvgDevice dev, FontFace face, float pointSize, signed long* coords) {
+VkvgFont _create_font_from_face (VkvgSurface surf, FontFace face, float pointSize, signed long* coords) {
VkvgFont font = (VkvgFont)calloc(1, sizeof(vkvg_font_t));
if (!font) {
LOGE("Create font failed, no memory\n");
@@ -1002,6 +1005,7 @@ VkvgFont _create_font_from_face (VkvgDevice dev, FontFace face, float pointSize,
}
font->face = face;
+ VkvgDevice dev = surf->dev;
#ifdef VKVG_USE_FREETYPE
if (dev->threadAware)
@@ -1027,7 +1031,8 @@ VkvgFont _create_font_from_face (VkvgDevice dev, FontFace face, float pointSize,
FT_CHECK_RES(FT_New_Size (face->face, &font->ftSize));
FT_CHECK_RES(FT_Activate_Size(font->ftSize));
- FT_CHECK_RES(FT_Set_Char_Size(face->face, 0, font->charSize, dev->hdpi, dev->vdpi));
+ //TODO:handle fixed sizes
+ FT_CHECK_RES(FT_Set_Char_Size(face->face, 0, font->charSize, surf->hdpi, surf->vdpi));
if (font->coords) {
FT_Set_Var_Design_Coordinates(face->face, font->face->numAxis, font->coords);
font->face->coords = font->coords;
@@ -1070,20 +1075,20 @@ VkvgFont _create_font_from_face (VkvgDevice dev, FontFace face, float pointSize,
return font;
}
-VkvgFont vkvg_font_create_from_file (VkvgDevice dev, const char* fontFilePath, int faceIndex, float pointSize) {
+VkvgFont vkvg_font_create_from_file (VkvgSurface surf, const char* fontFilePath, int faceIndex, float pointSize) {
FontFace face = NULL;
- if (!try_create_font_face_from_path(dev, fontFilePath, faceIndex, &face) || !face) {
+ if (!try_create_font_face_from_path(surf->dev, fontFilePath, faceIndex, &face) || !face) {
return NULL;
}
- return _create_font_from_face(dev, face, pointSize, NULL);
+ return _create_font_from_face(surf, face, pointSize, NULL);
}
-VkvgFont vkvg_font_create (VkvgDevice dev, const char* query, float pointSize) {
+VkvgFont vkvg_font_create (VkvgSurface surf, const char* query, float pointSize) {
uint32_t pt26_6 = (uint32_t)(pointSize * 64.f);
VkvgFont font = NULL;
FontFace face = NULL;
signed long* coords = NULL;
unsigned int numAxis = 0;
- if (try_get_or_create_font_face_from_query(dev, query, &face, &coords)) {
+ if (try_get_or_create_font_face_from_query(surf->dev, query, &face, &coords)) {
if (try_get_font_size(face, pt26_6, coords, &font)) {
vkvg_font_reference(font);
return font;
@@ -1092,7 +1097,7 @@ VkvgFont vkvg_font_create (VkvgDevice dev, const char* query, float pointSize) {
if (!face)
return NULL;
- return _create_font_from_face(dev, face, pointSize, coords);
+ return _create_font_from_face(surf, face, pointSize, coords);
}
VkvgFont vkvg_font_reference(VkvgFont font) {
if (!vkvg_font_status(font))
diff --git a/src/vkvg_surface.c b/src/vkvg_surface.c
index b52eea2..6d10df8 100644
--- a/src/vkvg_surface.c
+++ b/src/vkvg_surface.c
@@ -212,8 +212,27 @@ void vkvg_surface_destroy(VkvgSurface surf) {
LOG(VKVG_LOG_INFO, "DESTROY Surface\n");
+ VkvgDevice dev = surf->dev;
+
+#ifndef __APPLE__
+ vkDestroyPipeline(dev->vkDev, surf->pipelinePolyFill, NULL);
+#endif
+ vkDestroyPipeline(dev->vkDev, surf->pipelineClipping, NULL);
+
+ vkDestroyPipeline(dev->vkDev, surf->pipe_OVER, NULL);
+ vkDestroyPipeline(dev->vkDev, surf->pipe_SUB, NULL);
+ vkDestroyPipeline(dev->vkDev, surf->pipe_CLEAR, NULL);
+
+#ifdef VKVG_WIRED_DEBUG
+ vkDestroyPipeline(dev->vkDev, surf->pipelineWired, NULL);
+ vkDestroyPipeline(dev->vkDev, surf->pipelineLineList, NULL);
+#endif
+
vkDestroyCommandPool(surf->dev->vkDev, surf->cmdPool, NULL);
vkDestroyFramebuffer(surf->dev->vkDev, surf->fb, NULL);
+ vkDestroyRenderPass(surf->dev->vkDev, surf->renderPass, NULL);
+ vkDestroyRenderPass(surf->dev->vkDev, surf->renderPass_ClearStencil, NULL);
+ vkDestroyRenderPass(surf->dev->vkDev, surf->renderPass_ClearAll, NULL);
if (!surf->img->imported)
vkh_image_destroy(surf->img);
@@ -275,6 +294,18 @@ uint32_t vkvg_surface_get_height(VkvgSurface surf) {
return 0;
return surf->height;
}
+void vkvg_surface_set_dpy(VkvgSurface surf, int hdpy, int vdpy) {
+ if (vkvg_surface_status(surf))
+ return;
+ surf->hdpi = hdpy;
+ surf->vdpi = vdpy;
+}
+void vkvg_surface_get_dpy(VkvgSurface surf, int* hdpy, int* vdpy) {
+ if (vkvg_surface_status(surf))
+ return;
+ *hdpy = surf->hdpi;
+ *vdpy = surf->vdpi;
+}
vkvg_status_t vkvg_surface_write_to_png(VkvgSurface surf, const char* path) {
if (vkvg_surface_status(surf)) {
diff --git a/src/vkvg_surface_internal.c b/src/vkvg_surface_internal.c
index 8d15d2b..2c794f6 100644
--- a/src/vkvg_surface_internal.c
+++ b/src/vkvg_surface_internal.c
@@ -22,9 +22,13 @@
#include "vkvg_device_internal.h"
#include "vkvg_surface_internal.h"
+#include "vkvg_context_internal.h"
+
#include "vkh_image.h"
#include "vkh_queue.h"
+#include "shaders.h"
+
void _explicit_ms_resolve(VkvgSurface surf) {
LOCK_SURFACE(surf)
@@ -90,7 +94,7 @@ void _clear_surface(VkvgSurface surf, VkImageAspectFlags aspect) {
VkImageSubresourceRange range = {VK_IMAGE_ASPECT_COLOR_BIT, 0, 1, 0, 1};
VkhImage img = surf->imgMS;
- if (surf->dev->samples == VK_SAMPLE_COUNT_1_BIT)
+ if (surf->samples == VK_SAMPLE_COUNT_1_BIT)
img = surf->img;
vkh_image_set_layout(cmd, img, VK_IMAGE_ASPECT_COLOR_BIT, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
@@ -124,6 +128,332 @@ void _clear_surface(VkvgSurface surf, VkImageAspectFlags aspect) {
UNLOCK_SURFACE(surf)
}
+VkRenderPass _createRenderPassNoResolve(VkvgSurface surf, VkAttachmentLoadOp loadOp,
+ VkAttachmentLoadOp stencilLoadOp) {
+ VkAttachmentDescription attColor = {.format = FB_COLOR_FORMAT,
+ .samples = surf->samples,
+ .loadOp = loadOp,
+ .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
+ .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
+ .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
+ .initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
+ .finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
+ VkAttachmentDescription attDS = {.format = surf->dev->stencilFormat,
+ .samples = surf->samples,
+ .loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
+ .storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
+ .stencilLoadOp = stencilLoadOp,
+ .stencilStoreOp = VK_ATTACHMENT_STORE_OP_STORE,
+ .initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
+ .finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
+
+ VkAttachmentDescription attachments[] = {attColor, attDS};
+ VkAttachmentReference colorRef = {0, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
+ VkAttachmentReference dsRef = {1, VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
+
+ VkSubpassDescription subpassDescription = {.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS,
+ .colorAttachmentCount = 1,
+ .pColorAttachments = &colorRef,
+ .pDepthStencilAttachment = &dsRef};
+
+ VkSubpassDependency dependencies[] = {
+ {VK_SUBPASS_EXTERNAL, 0, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
+ VK_ACCESS_MEMORY_READ_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,
+ VK_DEPENDENCY_BY_REGION_BIT},
+ {0, VK_SUBPASS_EXTERNAL, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT,
+ VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, VK_ACCESS_MEMORY_READ_BIT,
+ VK_DEPENDENCY_BY_REGION_BIT},
+ };
+
+ VkRenderPassCreateInfo renderPassInfo = {.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
+ .attachmentCount = 2,
+ .pAttachments = attachments,
+ .subpassCount = 1,
+ .pSubpasses = &subpassDescription,
+ .dependencyCount = 2,
+ .pDependencies = dependencies};
+ VkRenderPass rp;
+ VK_CHECK_RESULT(vkCreateRenderPass(surf->dev->vkDev, &renderPassInfo, NULL, &rp));
+ return rp;
+}
+VkRenderPass _createRenderPassMS(VkvgSurface surf, VkAttachmentLoadOp loadOp, VkAttachmentLoadOp stencilLoadOp) {
+ VkAttachmentDescription attColor = {.format = FB_COLOR_FORMAT,
+ .samples = surf->samples,
+ .loadOp = loadOp,
+ .storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
+ .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
+ .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
+ .initialLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL,
+ .finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
+ VkAttachmentDescription attColorResolve = {.format = FB_COLOR_FORMAT,
+ .samples = VK_SAMPLE_COUNT_1_BIT,
+ .loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
+ .storeOp = VK_ATTACHMENT_STORE_OP_STORE,
+ .stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
+ .stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
+ .initialLayout = VK_IMAGE_LAYOUT_UNDEFINED,
+ .finalLayout = VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
+ VkAttachmentDescription attDS = {.format = surf->dev->stencilFormat,
+ .samples = surf->samples,
+ .loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE,
+ .storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE,
+ .stencilLoadOp = stencilLoadOp,
+ .stencilStoreOp = VK_ATTACHMENT_STORE_OP_STORE,
+ .initialLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
+ .finalLayout = VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
+
+ VkAttachmentDescription attachments[] = {attColorResolve, attDS, attColor};
+ VkAttachmentReference resolveRef = {0, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
+ VkAttachmentReference dsRef = {1, VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL};
+ VkAttachmentReference colorRef = {2, VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL};
+
+ VkSubpassDescription subpassDescription = {.pipelineBindPoint = VK_PIPELINE_BIND_POINT_GRAPHICS,
+ .colorAttachmentCount = 1,
+ .pColorAttachments = &colorRef,
+ .pResolveAttachments = &resolveRef,
+ .pDepthStencilAttachment = &dsRef};
+
+ VkSubpassDependency dependencies[] = {
+ {VK_SUBPASS_EXTERNAL, 0, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT,
+ VK_ACCESS_MEMORY_READ_BIT, VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT,
+ VK_DEPENDENCY_BY_REGION_BIT},
+ {0, VK_SUBPASS_EXTERNAL, VK_PIPELINE_STAGE_COLOR_ATTACHMENT_OUTPUT_BIT, VK_PIPELINE_STAGE_BOTTOM_OF_PIPE_BIT,
+ VK_ACCESS_COLOR_ATTACHMENT_READ_BIT | VK_ACCESS_COLOR_ATTACHMENT_WRITE_BIT, VK_ACCESS_MEMORY_READ_BIT,
+ VK_DEPENDENCY_BY_REGION_BIT},
+ };
+
+ VkRenderPassCreateInfo renderPassInfo = {.sType = VK_STRUCTURE_TYPE_RENDER_PASS_CREATE_INFO,
+ .attachmentCount = 3,
+ .pAttachments = attachments,
+ .subpassCount = 1,
+ .pSubpasses = &subpassDescription,
+ .dependencyCount = 2,
+ .pDependencies = dependencies};
+ VkRenderPass rp;
+ VK_CHECK_RESULT(vkCreateRenderPass(surf->dev->vkDev, &renderPassInfo, NULL, &rp));
+ return rp;
+}
+void _setupPipelines(VkvgSurface surf) {
+ VkvgDevice dev = surf->dev;
+ VkGraphicsPipelineCreateInfo pipelineCreateInfo = {.sType = VK_STRUCTURE_TYPE_GRAPHICS_PIPELINE_CREATE_INFO,
+ .renderPass = surf->renderPass};
+
+ VkPipelineInputAssemblyStateCreateInfo inputAssemblyState = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
+ .topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_FAN};
+
+ VkPipelineRasterizationStateCreateInfo rasterizationState = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
+ .polygonMode = VK_POLYGON_MODE_FILL,
+ .cullMode = VK_CULL_MODE_NONE,
+ .frontFace = VK_FRONT_FACE_COUNTER_CLOCKWISE,
+ .depthClampEnable = VK_FALSE,
+ .rasterizerDiscardEnable = VK_FALSE,
+ .depthBiasEnable = VK_FALSE,
+ .lineWidth = 1.0f};
+
+ VkPipelineColorBlendAttachmentState blendAttachmentState = {
+ .colorWriteMask = 0x0,
+ .blendEnable = VK_TRUE,
+#ifdef VKVG_PREMULT_ALPHA
+ .srcColorBlendFactor = VK_BLEND_FACTOR_ONE,
+ .dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA,
+ .colorBlendOp = VK_BLEND_OP_ADD,
+ .srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE,
+ .dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA,
+ .alphaBlendOp = VK_BLEND_OP_ADD,
+#else
+ .srcColorBlendFactor = VK_BLEND_FACTOR_SRC_ALPHA,
+ .dstColorBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA,
+ .colorBlendOp = VK_BLEND_OP_ADD,
+ .srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE,
+ .dstAlphaBlendFactor = VK_BLEND_FACTOR_ZERO,
+ .alphaBlendOp = VK_BLEND_OP_ADD,
+#endif
+ };
+
+ VkPipelineColorBlendStateCreateInfo colorBlendState = {.sType =
+ VK_STRUCTURE_TYPE_PIPELINE_COLOR_BLEND_STATE_CREATE_INFO,
+ .attachmentCount = 1,
+ .pAttachments = &blendAttachmentState};
+
+ /*failOp,passOp,depthFailOp,compareOp, compareMask, writeMask, reference;*/
+ VkStencilOpState polyFillOpState = {VK_STENCIL_OP_KEEP,
+ VK_STENCIL_OP_INVERT,
+ VK_STENCIL_OP_KEEP,
+ VK_COMPARE_OP_EQUAL,
+ STENCIL_CLIP_BIT,
+ STENCIL_FILL_BIT,
+ 0};
+ VkStencilOpState clipingOpState = {VK_STENCIL_OP_ZERO,
+ VK_STENCIL_OP_REPLACE,
+ VK_STENCIL_OP_KEEP,
+ VK_COMPARE_OP_EQUAL,
+ STENCIL_FILL_BIT,
+ STENCIL_ALL_BIT,
+ 0x2};
+ VkStencilOpState stencilOpState = {VK_STENCIL_OP_KEEP,
+ VK_STENCIL_OP_ZERO,
+ VK_STENCIL_OP_KEEP,
+ VK_COMPARE_OP_EQUAL,
+ STENCIL_FILL_BIT,
+ STENCIL_FILL_BIT,
+ 0x1};
+
+ VkPipelineDepthStencilStateCreateInfo dsStateCreateInfo = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
+ .depthTestEnable = VK_FALSE,
+ .depthWriteEnable = VK_FALSE,
+ .depthCompareOp = VK_COMPARE_OP_ALWAYS,
+ .stencilTestEnable = VK_TRUE,
+ .front = polyFillOpState,
+ .back = polyFillOpState};
+
+ VkDynamicState dynamicStateEnables[] = {
+ VK_DYNAMIC_STATE_VIEWPORT,
+ VK_DYNAMIC_STATE_SCISSOR,
+ VK_DYNAMIC_STATE_STENCIL_COMPARE_MASK,
+ VK_DYNAMIC_STATE_STENCIL_REFERENCE,
+ VK_DYNAMIC_STATE_STENCIL_WRITE_MASK,
+ };
+ VkPipelineDynamicStateCreateInfo dynamicState = {.sType = VK_STRUCTURE_TYPE_PIPELINE_DYNAMIC_STATE_CREATE_INFO,
+ .dynamicStateCount = 2,
+ .pDynamicStates = dynamicStateEnables};
+
+ VkPipelineViewportStateCreateInfo viewportState = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_VIEWPORT_STATE_CREATE_INFO, .viewportCount = 1, .scissorCount = 1};
+
+ VkPipelineMultisampleStateCreateInfo multisampleState = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_MULTISAMPLE_STATE_CREATE_INFO, .rasterizationSamples = VK_SAMPLE_COUNT_1_BIT};
+ /*if (dev->samples != VK_SAMPLE_COUNT_1_BIT){
+ multisampleState.sampleShadingEnable = VK_TRUE;
+ multisampleState.minSampleShading = 0.5f;
+ }*/
+ VkVertexInputBindingDescription vertexInputBinding = {
+ .binding = 0, .stride = sizeof(Vertex), .inputRate = VK_VERTEX_INPUT_RATE_VERTEX};
+
+ VkVertexInputAttributeDescription vertexInputAttributs[3] = {{0, 0, VK_FORMAT_R32G32_SFLOAT, 0},
+ {1, 0, VK_FORMAT_R8G8B8A8_UNORM, 8},
+ {2, 0, VK_FORMAT_R32G32B32_SFLOAT, 12}};
+
+ VkPipelineVertexInputStateCreateInfo vertexInputState = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
+ .vertexBindingDescriptionCount = 1,
+ .pVertexBindingDescriptions = &vertexInputBinding,
+ .vertexAttributeDescriptionCount = 3,
+ .pVertexAttributeDescriptions = vertexInputAttributs};
+#ifdef VKVG_WIRED_DEBUG
+ VkShaderModule modVert, modFrag, modFragWired;
+#else
+ VkShaderModule modVert, modFrag;
+#endif
+ VkShaderModuleCreateInfo createInfo = {.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO,
+ .pCode = (uint32_t*)vkvg_main_vert_spv,
+ .codeSize = vkvg_main_vert_spv_len};
+ VK_CHECK_RESULT(vkCreateShaderModule(dev->vkDev, &createInfo, NULL, &modVert));
+#if defined(VKVG_LCD_FONT_FILTER) && defined(FT_CONFIG_OPTION_SUBPIXEL_RENDERING)
+ createInfo.pCode = (uint32_t*)vkvg_main_lcd_frag_spv;
+ createInfo.codeSize = vkvg_main_lcd_frag_spv_len;
+#else
+ createInfo.pCode = (uint32_t*)vkvg_main_frag_spv;
+ createInfo.codeSize = vkvg_main_frag_spv_len;
+#endif
+ VK_CHECK_RESULT(vkCreateShaderModule(dev->vkDev, &createInfo, NULL, &modFrag));
+
+ VkPipelineShaderStageCreateInfo vertStage = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
+ .stage = VK_SHADER_STAGE_VERTEX_BIT,
+ .module = modVert,
+ .pName = "main",
+ };
+ VkPipelineShaderStageCreateInfo fragStage = {
+ .sType = VK_STRUCTURE_TYPE_PIPELINE_SHADER_STAGE_CREATE_INFO,
+ .stage = VK_SHADER_STAGE_FRAGMENT_BIT,
+ .module = modFrag,
+ .pName = "main",
+ };
+
+ // Use specialization constants to pass number of samples to the shader (used for MSAA resolve)
+ /*VkSpecializationMapEntry specializationEntry = {
+ .constantID = 0,
+ .offset = 0,
+ .size = sizeof(uint32_t)};
+ uint32_t specializationData = VKVG_SAMPLES;
+ VkSpecializationInfo specializationInfo = {
+ .mapEntryCount = 1,
+ .pMapEntries = &specializationEntry,
+ .dataSize = sizeof(specializationData),
+ .pData = &specializationData};*/
+
+ VkPipelineShaderStageCreateInfo shaderStages[] = {vertStage, fragStage};
+
+ pipelineCreateInfo.stageCount = 1;
+ pipelineCreateInfo.pStages = shaderStages;
+ pipelineCreateInfo.pVertexInputState = &vertexInputState;
+ pipelineCreateInfo.pInputAssemblyState = &inputAssemblyState;
+ pipelineCreateInfo.pViewportState = &viewportState;
+ pipelineCreateInfo.pRasterizationState = &rasterizationState;
+ pipelineCreateInfo.pMultisampleState = &multisampleState;
+ pipelineCreateInfo.pColorBlendState = &colorBlendState;
+ pipelineCreateInfo.pDepthStencilState = &dsStateCreateInfo;
+ pipelineCreateInfo.pDynamicState = &dynamicState;
+ pipelineCreateInfo.layout = dev->pipelineLayout;
+
+#ifndef __APPLE__
+ VK_CHECK_RESULT(vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL,
+ &surf->pipelinePolyFill));
+#endif
+
+ inputAssemblyState.topology = VK_PRIMITIVE_TOPOLOGY_TRIANGLE_LIST;
+ dsStateCreateInfo.back = dsStateCreateInfo.front = clipingOpState;
+ dynamicState.dynamicStateCount = 5;
+ VK_CHECK_RESULT(vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL,
+ &surf->pipelineClipping));
+
+ dsStateCreateInfo.back = dsStateCreateInfo.front = stencilOpState;
+ blendAttachmentState.colorWriteMask = 0xf;
+ dynamicState.dynamicStateCount = 3;
+ pipelineCreateInfo.stageCount = 2;
+ VK_CHECK_RESULT(
+ vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &surf->pipe_OVER));
+
+ blendAttachmentState.alphaBlendOp = blendAttachmentState.colorBlendOp = VK_BLEND_OP_SUBTRACT;
+ VK_CHECK_RESULT(
+ vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &surf->pipe_SUB));
+
+ colorBlendState.logicOpEnable = VK_TRUE;
+ blendAttachmentState.blendEnable = VK_FALSE;
+ colorBlendState.logicOp = VK_LOGIC_OP_CLEAR;
+ VK_CHECK_RESULT(
+ vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &surf->pipe_CLEAR));
+
+#ifdef VKVG_WIRED_DEBUG
+ colorBlendState.logicOpEnable = VK_FALSE;
+ blendAttachmentState.blendEnable = VK_TRUE;
+ colorBlendState.logicOp = VK_LOGIC_OP_CLEAR;
+
+ createInfo.pCode = (uint32_t*)wired_frag_spv;
+
+ createInfo.codeSize = wired_frag_spv_len;
+ VK_CHECK_RESULT(vkCreateShaderModule(dev->vkDev, &createInfo, NULL, &modFragWired));
+
+ shaderStages[1].module = modFragWired;
+
+ rasterizationState.polygonMode = VK_POLYGON_MODE_LINE;
+ VK_CHECK_RESULT(vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL,
+ &dev->pipelineLineList));
+
+ inputAssemblyState.topology = VK_PRIMITIVE_TOPOLOGY_POINT_LIST;
+ rasterizationState.polygonMode = VK_POLYGON_MODE_FILL;
+ VK_CHECK_RESULT(
+ vkCreateGraphicsPipelines(dev->vkDev, dev->pipelineCache, 1, &pipelineCreateInfo, NULL, &dev->pipelineWired));
+
+ vkDestroyShaderModule(dev->vkDev, modFragWired, NULL);
+#endif
+
+ vkDestroyShaderModule(dev->vkDev, modVert, NULL);
+ vkDestroyShaderModule(dev->vkDev, modFrag, NULL);
+}
void _create_surface_main_image(VkvgSurface surf) {
VkhDevice vkhd = (VkhDevice)&surf->dev->vkDev;
@@ -145,9 +475,9 @@ void _create_surface_main_image(VkvgSurface surf) {
// create multisample color img if sample count > 1 and the stencil buffer multisampled or not
void _create_surface_secondary_images(VkvgSurface surf) {
VkhDevice vkhd = (VkhDevice)&surf->dev->vkDev;
- if (surf->dev->samples > VK_SAMPLE_COUNT_1_BIT) {
+ if (surf->samples > VK_SAMPLE_COUNT_1_BIT) {
surf->imgMS = vkh_image_ms_create(
- vkhd, surf->format, surf->dev->samples, surf->width, surf->height, VKH_MEMORY_USAGE_GPU_ONLY,
+ vkhd, surf->format, surf->samples, surf->width, surf->height, VKH_MEMORY_USAGE_GPU_ONLY,
VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT);
vkh_image_create_descriptor(surf->imgMS, VK_IMAGE_VIEW_TYPE_2D, VK_IMAGE_ASPECT_COLOR_BIT, VK_FILTER_NEAREST,
VK_FILTER_NEAREST, VK_SAMPLER_MIPMAP_MODE_NEAREST,
@@ -160,7 +490,7 @@ void _create_surface_secondary_images(VkvgSurface surf) {
"SURF MS color SAMPLER");
#endif
}
- surf->stencil = vkh_image_ms_create(vkhd, surf->dev->stencilFormat, surf->dev->samples, surf->width, surf->height,
+ surf->stencil = vkh_image_ms_create(vkhd, surf->dev->stencilFormat, surf->samples, surf->width, surf->height,
VKH_MEMORY_USAGE_GPU_ONLY,
VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT |
VK_IMAGE_USAGE_TRANSFER_SRC_BIT);
@@ -182,13 +512,13 @@ void _create_framebuffer(VkvgSurface surf) {
vkh_image_get_view(surf->imgMS),
};
VkFramebufferCreateInfo frameBufferCreateInfo = {.sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO,
- .renderPass = surf->dev->renderPass,
+ .renderPass = surf->renderPass,
.attachmentCount = 3,
.pAttachments = attachments,
.width = surf->width,
.height = surf->height,
.layers = 1};
- if (surf->dev->samples == VK_SAMPLE_COUNT_1_BIT)
+ if (surf->samples == VK_SAMPLE_COUNT_1_BIT)
frameBufferCreateInfo.attachmentCount = 2;
else if (surf->dev->deferredResolve) {
attachments[0] = attachments[2];
@@ -225,14 +555,35 @@ VkvgSurface _create_surface(VkvgDevice dev, VkFormat format) {
}
atomic_init(&surf->references, 1);
- surf->dev = dev;
- surf->format = format;
+ surf->dev = dev;
+ surf->format = format;
+ surf->hdpi = 72;
+ surf->vdpi = 72;
+ surf->samples = VK_SAMPLE_COUNT_1_BIT;
if (dev->threadAware)
mtx_init(&surf->mutex, mtx_plain);
VkhDevice vkhd = (VkhDevice)&surf->dev->vkDev;
+ if (dev->deferredResolve || surf->samples == VK_SAMPLE_COUNT_1_BIT) {
+ surf->renderPass =
+ _createRenderPassNoResolve(surf, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_LOAD);
+ surf->renderPass_ClearStencil =
+ _createRenderPassNoResolve(surf, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_CLEAR);
+ surf->renderPass_ClearAll =
+ _createRenderPassNoResolve(surf, VK_ATTACHMENT_LOAD_OP_CLEAR, VK_ATTACHMENT_LOAD_OP_CLEAR);
+ } else {
+ surf->renderPass =
+ _createRenderPassMS(surf, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_LOAD);
+ surf->renderPass_ClearStencil =
+ _createRenderPassMS(surf, VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_LOAD_OP_CLEAR);
+ surf->renderPass_ClearAll =
+ _createRenderPassMS(surf, VK_ATTACHMENT_LOAD_OP_CLEAR, VK_ATTACHMENT_LOAD_OP_CLEAR);
+ }
+
+ _setupPipelines(surf);
+
surf->cmdPool =
vkh_cmd_pool_create(vkhd, dev->gQueue->familyIndex, VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT);
vkh_cmd_buffs_create(vkhd, surf->cmdPool, VK_COMMAND_BUFFER_LEVEL_PRIMARY, 1, &surf->cmd);
@@ -245,6 +596,17 @@ VkvgSurface _create_surface(VkvgDevice dev, VkFormat format) {
#if defined(DEBUG) && defined(VKVG_DBG_UTILS)
vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_COMMAND_BUFFER, (uint64_t)surf->cmd, "vkvgSurfCmd");
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_RENDER_PASS, (uint64_t)surf->renderPass, "RP load img/stencil");
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_RENDER_PASS, (uint64_t)surf->renderPass_ClearStencil, "RP clear stencil");
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_RENDER_PASS, (uint64_t)surf->renderPass_ClearAll, "RP clear all");
+#ifndef __APPLE__
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)surf->pipelinePolyFill, "PL Poly fill");
+#endif
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)surf->pipelineClipping, "PL Clipping");
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)surf->pipe_OVER, "PL draw Over");
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)surf->pipe_SUB, "PL draw Substract");
+ vkh_device_set_object_name(vkhd, VK_OBJECT_TYPE_PIPELINE, (uint64_t)surf->pipe_CLEAR, "PL draw Clear");
+
#endif
vkvg_device_reference(surf->dev);
return surf;
diff --git a/src/vkvg_surface_internal.h b/src/vkvg_surface_internal.h
index ee0be34..2c2af93 100644
--- a/src/vkvg_surface_internal.h
+++ b/src/vkvg_surface_internal.h
@@ -47,7 +47,17 @@ typedef struct _vkvg_surface_t {
#else
VkFence flushFence; // unsignaled idle.
#endif
-
+ int hdpi, /**< only used for FreeType fonts and svg loading */
+ vdpi;
+ VkSampleCountFlags samples; /**< samples count */
+ VkRenderPass renderPass; /**< Vulkan render pass, common for all surfaces */
+ VkRenderPass renderPass_ClearStencil; /**< Vulkan render pass for first draw with context, stencil has to be cleared */
+ VkRenderPass renderPass_ClearAll; /**< Vulkan render pass for new surface, clear all attacments*/
+ VkPipeline pipe_OVER; /**< default operator */
+ VkPipeline pipe_SUB;
+ VkPipeline pipe_CLEAR; /**< clear operator */
+ VkPipeline pipelinePolyFill; /**< even-odd polygon filling first step */
+ VkPipeline pipelineClipping; /**< draw on stencil to update clipping regions */
} vkvg_surface;
#define LOCK_SURFACE(surf) \
diff --git a/tests/common/test.c b/tests/common/test.c
index 00bf912..fde3317 100644
--- a/tests/common/test.c
+++ b/tests/common/test.c
@@ -48,7 +48,7 @@ int single_test = -1; // if not < 0, contains the index of the single test to ru
static bool paused = false;
static bool offscreen = false;
static bool threadAware = false;
-static VkSampleCountFlags samples = VK_SAMPLE_COUNT_4_BIT;
+static VkSampleCountFlags samples = VK_SAMPLE_COUNT_1_BIT;
static VkPhysicalDeviceType preferedPhysicalDeviceType = VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU;
static vk_engine_t* e;
static char* saveToPng = NULL;
@@ -503,7 +503,7 @@ void perform_test_offscreen(void (*testfunc)(void), const char* testName, int ar
void perform_test_onscreen(void (*testfunc)(void), const char* testName, int argc, char* argv[]) {
init_test(test_width, test_height);
- vkvg_device_set_dpy(device, 96, 96);
+ vkvg_surface_set_dpy(surf, 96, 96);
#ifdef VKVG_TEST_DIRECT_DRAW
surfaces = (VkvgSurface*)malloc(r->imgCount * sizeof(VkvgSurface));
diff --git a/tests/fonts/allfont.c b/tests/fonts/allfont.c
index 4e79fa3..36e8952 100644
--- a/tests/fonts/allfont.c
+++ b/tests/fonts/allfont.c
@@ -172,7 +172,7 @@ void draw(VkvgSurface surfFont) {
char tmp[1024];
- VkvgFont mono = vkvg_font_create(device, "mono", 12);
+ VkvgFont mono = vkvg_font_create(surf, "mono", 12);
for (int i = curFontStartIdx; i < font_database->nfont; i++) {
FcPattern* font_entry = font_database->fonts[i];
@@ -199,7 +199,7 @@ void draw(VkvgSurface surfFont) {
if (onlyVariable && !variable)
continue;
- VkvgFont font = vkvg_font_create (device, tmp, fontSize);
+ VkvgFont font = vkvg_font_create (surf, tmp, fontSize);
if (vkvg_font_status(font)) {
printf("Error trying to load %s, from %s\n", tmp, file_path);
fflush(stdout);
@@ -340,8 +340,8 @@ int main(int argc, char* argv[]) {
e->gQFamIdx, 0, false };//, TESTS_DATA_ROOT "/fonts"};
device = vkvg_device_create(&info);
- vkvg_device_set_dpy(device, 96,96);
surf = vkvg_surface_create(device, test_width, test_height);
+ vkvg_surface_set_dpy(surf, 96,96);
VkvgSurface surfFont = vkvg_surface_create(device, test_width, test_height);
vkh_presenter_build_blit_cmd(r, vkvg_surface_get_vk_image(surf), test_width, test_height);
diff --git a/tests/fonts/fontquery.c b/tests/fonts/fontquery.c
index c4ab1f9..3cab712 100644
--- a/tests/fonts/fontquery.c
+++ b/tests/fonts/fontquery.c
@@ -282,7 +282,7 @@ void draw(VkvgSurface surfFont) {
FcPatternGetString (font, FC_FAMILY, 0, &family_name);
FcPatternGetString (font, FC_STYLE, 0, &style_variant);
FcPatternGetBool(font, FC_VARIABLE, 0, &var);
- VkvgFont f = vkvg_font_create_from_file(device, (char*)fontFile, index, fontSize);
+ VkvgFont f = vkvg_font_create_from_file(surf, (char*)fontFile, index, fontSize);
if (vkvg_font_status(f)) {
printf("Error trying to load %s, from %s\n", txtBuffCopy, fontFile);
fflush(stdout);
@@ -528,7 +528,7 @@ int main(int argc, char* argv[]) {
strcpy (txtBuffer, "sans");
txtBuffPtr = 4;
- sans16 = vkvg_font_create(device, "sans", 16);
+ sans16 = vkvg_font_create(surf, "sans", 16);
while (!vkengine_should_close(e)) {
glfwPollEvents();
diff --git a/tests/text.c b/tests/text.c
index 6e131ce..82f9c02 100644
--- a/tests/text.c
+++ b/tests/text.c
@@ -194,8 +194,8 @@ void simple_text() {
vkvg_paint(ctx);
vkvg_set_source_rgb(ctx, 1, 1, 1);
- VkvgFont mono = vkvg_font_create(device, "mono", 12);
- VkvgFont norm = vkvg_font_create_from_file(device, "data/Proto-Sinaitic15.ttf", 0, 24);
+ VkvgFont mono = vkvg_font_create(surf, "mono", 12);
+ VkvgFont norm = vkvg_font_create_from_file(surf, "data/Proto-Sinaitic15.ttf", 0, 24);
vkvg_set_font (ctx, mono);
vkvg_move_to(ctx, 20, 50);
vkvg_show_text(ctx, "hwhy");
@@ -228,7 +228,7 @@ void variable_text() {
vkvg_paint(ctx);
vkvg_set_source_rgb(ctx, 1, 1, 1);
- VkvgFont noto = vkvg_font_create(device, "Noto Sans JP:fontvariations=wght=150", 30);
+ VkvgFont noto = vkvg_font_create(surf, "Noto Sans JP:fontvariations=wght=150", 30);
vkvg_set_font (ctx, noto);
vkvg_move_to(ctx, 20, 50);
@@ -236,14 +236,14 @@ void variable_text() {
vkvg_font_destroy(noto);
- noto = vkvg_font_create(device, "Noto Sans JP:fontvariations=wght=900", 30);
+ noto = vkvg_font_create(surf, "Noto Sans JP:fontvariations=wght=900", 30);
vkvg_set_font (ctx, noto);
vkvg_move_to(ctx, 20, 150);
vkvg_show_text(ctx, txt2);
vkvg_font_destroy(noto);
- noto = vkvg_font_create(device, "Cantarell:fontvariations=wght=900", 30);
+ noto = vkvg_font_create(surf, "Cantarell:fontvariations=wght=900", 30);
vkvg_set_font (ctx, noto);
vkvg_move_to(ctx, 20, 200);
vkvg_show_text(ctx, txt);