From: Jean-Philippe Bruyère Date: Wed, 3 Oct 2018 09:08:35 +0000 (+0200) Subject: premult alpha, comments, frame msr in test X-Git-Tag: v0.1-alpha~107^2~10 X-Git-Url: https://git.osiis.dedyn.io/?a=commitdiff_plain;h=b02d9bc08dbb51e039a9ad85df210481011a2a04;p=jp%2Fvkvg.git premult alpha, comments, frame msr in test --- diff --git a/include/vkvg.h b/include/vkvg.h index dd67a88..dfba3a3 100644 --- a/include/vkvg.h +++ b/include/vkvg.h @@ -50,6 +50,11 @@ static uint8_t log_level = LOG_ERR;// LOG_INFO | LOG_DEBUG; #define LOG #endif +typedef enum _vkvg_status { + VKVG_STATUS_SUCCESS, + VKVG_STATUS_NO_MEMORY +}vkvg_status_t; + typedef enum _vkvg_direction { VKVG_HORIZONTAL = 0, VKVG_VERTICAL = 1 diff --git a/src/shaders.h b/src/shaders.h index 60640c7..d4d5e0e 100644 --- a/src/shaders.h +++ b/src/shaders.h @@ -1,5 +1,5 @@ unsigned char vkvg_main_frag_spv[] = { - 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x06, 0x00, 0x0d, 0x00, + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x07, 0x00, 0x0d, 0x00, 0xef, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x47, 0x4c, 0x53, 0x4c, 0x2e, 0x73, 0x74, 0x64, 0x2e, 0x34, 0x35, 0x30, @@ -484,7 +484,7 @@ unsigned char vkvg_main_frag_spv[] = { }; unsigned int vkvg_main_frag_spv_len = 5780; unsigned char wired_frag_spv[] = { - 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x06, 0x00, 0x0d, 0x00, + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x07, 0x00, 0x0d, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x47, 0x4c, 0x53, 0x4c, 0x2e, 0x73, 0x74, 0x64, 0x2e, 0x34, 0x35, 0x30, @@ -581,7 +581,7 @@ unsigned char wired_frag_spv[] = { }; unsigned int wired_frag_spv_len = 1120; unsigned char vkvg_main_vert_spv[] = { - 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x06, 0x00, 0x0d, 0x00, + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x07, 0x00, 0x0d, 0x00, 0x61, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x47, 0x4c, 0x53, 0x4c, 0x2e, 0x73, 0x74, 0x64, 0x2e, 0x34, 0x35, 0x30, @@ -808,7 +808,7 @@ unsigned char vkvg_main_vert_spv[] = { }; unsigned int vkvg_main_vert_spv_len = 2680; unsigned char shader_comp_spv[] = { - 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x06, 0x00, 0x0d, 0x00, + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x07, 0x00, 0x0d, 0x00, 0xa1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x47, 0x4c, 0x53, 0x4c, 0x2e, 0x73, 0x74, 0x64, 0x2e, 0x34, 0x35, 0x30, @@ -1110,7 +1110,7 @@ unsigned char shader_comp_spv[] = { }; unsigned int shader_comp_spv_len = 3580; unsigned char shader2_comp_spv[] = { - 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x06, 0x00, 0x0d, 0x00, + 0x03, 0x02, 0x23, 0x07, 0x00, 0x00, 0x01, 0x00, 0x07, 0x00, 0x0d, 0x00, 0x6c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x00, 0x0b, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x47, 0x4c, 0x53, 0x4c, 0x2e, 0x73, 0x74, 0x64, 0x2e, 0x34, 0x35, 0x30, diff --git a/src/vkvg_context.c b/src/vkvg_context.c index 99ebcf9..d041024 100644 --- a/src/vkvg_context.c +++ b/src/vkvg_context.c @@ -38,6 +38,9 @@ VkvgContext vkvg_create(VkvgSurface surf) VkvgDevice dev = surf->dev; VkvgContext ctx = (vkvg_context*)calloc(1, sizeof(vkvg_context)); + if (ctx==NULL) + return NULL; + ctx->sizePoints = VKVG_PTS_SIZE; ctx->sizeVertices = VKVG_VBO_SIZE; ctx->sizeIndices = VKVG_IBO_SIZE; diff --git a/src/vkvg_context_internal.c b/src/vkvg_context_internal.c index 18ba758..c4588db 100644 --- a/src/vkvg_context_internal.c +++ b/src/vkvg_context_internal.c @@ -354,8 +354,8 @@ void _update_cur_pattern (VkvgContext ctx, VkvgPattern pat) { { VkvgSurface surf = (VkvgSurface)pat->data; - //flush ctx in two steps to add the src transition in the cmd buff - if (ctx->cmdStarted)//transition of img without appropriate dep in subpass must be done outside renderpass. + //flush ctx in two steps to add the src transitioning in the cmd buff + if (ctx->cmdStarted)//transition of img without appropriate dependencies in subpass must be done outside renderpass. _end_render_pass (ctx); else { vkh_cmd_begin (ctx->cmd,VK_COMMAND_BUFFER_USAGE_ONE_TIME_SUBMIT_BIT); diff --git a/src/vkvg_context_internal.h b/src/vkvg_context_internal.h index e0282d7..5ce5275 100644 --- a/src/vkvg_context_internal.h +++ b/src/vkvg_context_internal.h @@ -80,38 +80,38 @@ typedef struct _vkvg_context_save_t{ typedef struct _vkvg_context_t { VkvgContext pPrev; //double linked list of contexts VkvgContext pNext; - uint32_t references; + uint32_t references; //reference count - VkvgSurface pSurf; - VkFence flushFence; + VkvgSurface pSurf; //surface bound to context, set on creation of ctx + VkFence flushFence; //context fence VkhImage source; //source of painting operation - VkCommandPool cmdPool;//local pools ensure thread safety - VkCommandBuffer cmd; //single cmd buff for context operations - bool cmdStarted;//prevent flushing empty renderpass + VkCommandPool cmdPool; //local pools ensure thread safety + VkCommandBuffer cmd; //single cmd buff for context operations + bool cmdStarted; //prevent flushing empty renderpass bool pushCstDirty;//prevent pushing to gpu if not requested - VkDescriptorPool descriptorPool; - VkDescriptorSet dsFont; //fonts glyphs texture atlas descriptor (local for thread safety) - VkDescriptorSet dsSrc; //source ds - VkDescriptorSet dsGrad; //gradient uniform buffer + VkDescriptorPool descriptorPool;//one pool per thread + VkDescriptorSet dsFont; //fonts glyphs texture atlas descriptor (local for thread safety) + VkDescriptorSet dsSrc; //source ds + VkDescriptorSet dsGrad; //gradient uniform buffer - vkvg_buff uboGrad;//uniform buff obj holdings gradient infos + vkvg_buff uboGrad; //uniform buff obj holdings gradient infos //vk buffers, holds data until flush vkvg_buff indices; //index buffer with persistent map memory size_t sizeIndices; //reserved size uint32_t indCount; //current indice count - uint32_t curIndStart; + uint32_t curIndStart; //last index recorded in cmd buff vkvg_buff vertices; //vertex buffer with persistent mapped memory size_t sizeVertices; //reserved size uint32_t vertCount; //effective vertices count //pathes, exists until stroke of fill - vec2* points; //points array - size_t sizePoints; //reserved size - uint32_t pointCount; //effective points count + vec2* points; //points array + size_t sizePoints; //reserved size + uint32_t pointCount; //effective points count uint32_t pathPtr; //pathes array is a list of couple (start,end) point idx refering to point array @@ -133,6 +133,7 @@ typedef struct _vkvg_context_t { push_constants pushConsts; VkvgPattern pattern; + vkvg_status_t status; vkvg_context_save_t* pSavedCtxs;//last ctx saved ptr diff --git a/src/vkvg_device_internal.c b/src/vkvg_device_internal.c index 906e406..518741e 100644 --- a/src/vkvg_device_internal.c +++ b/src/vkvg_device_internal.c @@ -128,10 +128,10 @@ void _setupPipelines(VkvgDevice dev) VkPipelineColorBlendAttachmentState blendAttachmentState = { .colorWriteMask = 0x0, .blendEnable = VK_TRUE, .srcColorBlendFactor = VK_BLEND_FACTOR_ONE, - .dstColorBlendFactor= VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, - .colorBlendOp = VK_BLEND_OP_ADD, .srcAlphaBlendFactor = VK_BLEND_FACTOR_ONE, + .dstColorBlendFactor= VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, .dstAlphaBlendFactor = VK_BLEND_FACTOR_ONE_MINUS_SRC_ALPHA, + .colorBlendOp = VK_BLEND_OP_ADD, .alphaBlendOp = VK_BLEND_OP_ADD, }; diff --git a/src/vkvg_pattern.c b/src/vkvg_pattern.c index 767f701..ba74bf5 100644 --- a/src/vkvg_pattern.c +++ b/src/vkvg_pattern.c @@ -40,10 +40,11 @@ VkvgPattern vkvg_pattern_create_rgba (float r, float g, float b, float a){ pat->type = VKVG_PATTERN_TYPE_SOLID; pat->extend = VKVG_EXTEND_NONE; vkvg_color_t* c = (vkvg_color_t*)calloc(1,sizeof(vkvg_color_t)); - c->r = r; - c->g = g; - c->b = b; - c->a = a; + //premultiplied alpha + c->r = r * a; + c->g = g * a; + c->b = b * a; + c->a = a;// > 0.f ? 1.f : 0.f; pat->data = c; pat->references = 1; diff --git a/src/vkvg_surface.c b/src/vkvg_surface.c index 0323d2a..75282ce 100644 --- a/src/vkvg_surface.c +++ b/src/vkvg_surface.c @@ -306,7 +306,7 @@ void vkvg_surface_write_to_png (VkvgSurface surf, const char* path){ }; vkCmdBlitImage (cmd, vkh_image_get_vkimage (surf->img), VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, - vkh_image_get_vkimage (stagImg), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &blit, VK_FILTER_LINEAR); + vkh_image_get_vkimage (stagImg), VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &blit, VK_FILTER_NEAREST); vkh_cmd_end (cmd); vkh_cmd_submit (dev->gQueue, &cmd, dev->fence); diff --git a/tests/test1.c b/tests/test1.c index 12407f7..7312e18 100644 --- a/tests/test1.c +++ b/tests/test1.c @@ -20,7 +20,9 @@ * THE SOFTWARE. */ #include "vkengine.h" - +#include "stdio.h" +#include "stdlib.h" +#include "time.h" #include "vkvg.h" #include "string.h" //for nanosvg @@ -45,6 +47,26 @@ static void char_callback (GLFWwindow* window, uint32_t c){} static void mouse_move_callback(GLFWwindow* window, double x, double y){} static void mouse_button_callback(GLFWwindow* window, int but, int state, int modif){} +double time_diff(struct timeval x , struct timeval y) +{ + double x_ms , y_ms , diff; + + x_ms = (double)x.tv_sec*1000000 + (double)x.tv_usec; + y_ms = (double)y.tv_sec*1000000 + (double)y.tv_usec; + + diff = (double)y_ms - (double)x_ms; + + return diff; +} + +void randomize_color (VkvgContext ctx) { + vkvg_set_source_rgba(ctx, + (float)rand()/RAND_MAX, + (float)rand()/RAND_MAX, + (float)rand()/RAND_MAX, + (float)rand()/RAND_MAX + ); +} void vkvg_test_gradient (VkvgContext ctx) { VkvgPattern pat = vkvg_pattern_create_linear(100,0,300,0); vkvg_set_line_width(ctx, 20); @@ -831,28 +853,6 @@ void cairo_tests () { vkvg_paint(ctx); vkvg_set_matrix(ctx,&mat); - /* - vkvg_set_source_rgba(ctx,0,1,0,1); - vkvg_rectangle(ctx,0,0,600,600); - vkvg_fill(ctx); - - vkvg_clip(ctx); - - vkvg_set_source_rgba(ctx,1,0,0,1); - vkvg_paint(ctx); - //vkvg_rectangle(ctx,00,00,1024,800); - //vkvg_fill(ctx); - - vkvg_reset_clip(ctx); - vkvg_set_source_rgba(ctx,0,0,1,1); - vkvg_set_line_width(ctx,20); - vkvg_move_to(ctx,0,0); - vkvg_rel_line_to(ctx,800,800); - vkvg_stroke(ctx);*/ - -// cairo_test_clip(ctx); -// vkvg_reset_clip(ctx); - //test_img_surface (ctx); cairo_print_arc(ctx); @@ -862,15 +862,6 @@ void cairo_tests () { vkvg_translate(ctx,250,0); cairo_test_rounded_rect(ctx); - -/* - vkvg_set_operator(ctx, VKVG_OPERATOR_CLEAR); - vkvg_rectangle(ctx,100,100,500,500); - vkvg_fill(ctx); - vkvg_set_operator(ctx, VKVG_OPERATOR_OVER); -*/ - - vkvg_translate(ctx,-450,250); cairo_test_fill_and_stroke2(ctx); @@ -1061,15 +1052,42 @@ void simple_paint () { vkvg_paint(ctx); vkvg_destroy(ctx); } +void random_rectangles () { + vkvg_surface_clear(surf); + struct timeval currentTime; + gettimeofday(¤tTime, NULL); + + srand((unsigned) currentTime.tv_usec); + const float w = 1024.f; + + VkvgContext ctx = vkvg_create(surf); + vkvg_set_line_width(ctx,1); + for (int i=0; i<5000; i++) { + randomize_color(ctx); + float x = trunc( (0.5*(float)w*rand())/RAND_MAX ); + float y = trunc( (0.5*(float)w*rand())/RAND_MAX ); + float z = trunc( (0.5*(float)w*rand())/RAND_MAX ) + 1; + float v = trunc( (0.5*(float)w*rand())/RAND_MAX ) + 1; + + vkvg_rectangle(ctx, x+1, y+1, z, v); + vkvg_fill_preserve(ctx); + randomize_color(ctx); + vkvg_stroke(ctx); + } + vkvg_destroy(ctx); +} + void simple_rectangle_fill () { vkvg_surface_clear(surf); VkvgContext ctx = vkvg_create(surf); + vkvg_set_line_width(ctx,10); - vkvg_set_source_rgba(ctx,0,0,1,0.2); + vkvg_set_source_rgba(ctx,0,0,1,0.5); vkvg_rectangle(ctx,100,100,200,200); - vkvg_fill_preserve(ctx); - vkvg_set_source_rgba(ctx,1,0,0,0.2); - vkvg_stroke(ctx); + vkvg_fill(ctx); + vkvg_rectangle(ctx,200,200,200,200); + vkvg_set_source_rgba(ctx,1,0,0,0.5); + vkvg_fill(ctx); vkvg_destroy(ctx); } void simple_rectangle_stroke () { @@ -1108,9 +1126,17 @@ int main(int argc, char *argv[]) { vkh_presenter_build_blit_cmd (r, vkvg_surface_get_vk_image(surf), width, height); + struct timeval before , after; + double frameTime = 0, frameTimeAccum = 0, frameCount = 0; + while (!vkengine_should_close (e)) { glfwPollEvents(); + + gettimeofday(&before , NULL); + cairo_tests(); + //random_rectangles(); + //simple_rectangle_stroke(); //test_1(); //vkvg_surface_clear(surf); //simple_paint(); @@ -1123,8 +1149,16 @@ int main(int argc, char *argv[]) { //lines_stroke(); if (!vkh_presenter_draw (r)) vkh_presenter_build_blit_cmd (r, vkvg_surface_get_vk_image(surf), width, height); + + gettimeofday(&after , NULL); + + frameTimeAccum += time_diff(before , after); + frameCount++; } + frameTime = frameTimeAccum / frameCount; + printf ("frame (µs): %.0lf\nfps: %lf\n", frameTime, floor(1000000 / frameTime)); + vkDeviceWaitIdle(e->dev->dev); vkvg_surface_destroy (surf); diff --git a/tests/vkengine.c b/tests/vkengine.c index 7dc0c3e..f5655fa 100644 --- a/tests/vkengine.c +++ b/tests/vkengine.c @@ -86,7 +86,7 @@ vk_engine_t* vkengine_create (VkPhysicalDeviceType preferedGPU, uint32_t width, glfwWindowHint(GLFW_CLIENT_API, GLFW_NO_API); glfwWindowHint(GLFW_RESIZABLE, GLFW_TRUE); glfwWindowHint(GLFW_FLOATING, GLFW_FALSE); - glfwWindowHint(GLFW_DECORATED, GLFW_FALSE); + glfwWindowHint(GLFW_DECORATED, GLFW_TRUE); e->window = glfwCreateWindow (width, height, "Window Title", NULL, NULL); VkSurfaceKHR surf; @@ -173,7 +173,7 @@ vk_engine_t* vkengine_create (VkPhysicalDeviceType preferedGPU, uint32_t width, e->dev = vkh_device_create(pi->phy, dev); e->renderer = vkh_presenter_create - (e->dev, pi->pQueue, surf, width, height, VK_FORMAT_B8G8R8A8_UNORM, VK_PRESENT_MODE_FIFO_KHR); + (e->dev, pi->pQueue, surf, width, height, VK_FORMAT_B8G8R8A8_UNORM, VK_PRESENT_MODE_MAILBOX_KHR); vkh_app_free_phyinfos (phyCount, phys);