summaryrefslogtreecommitdiff
path: root/src/lib/ector/software
diff options
context:
space:
mode:
authorHermet Park <hermetpark@gmail.com>2018-12-07 19:38:48 +0900
committerHermet Park <hermetpark@gmail.com>2018-12-07 19:50:08 +0900
commitfbe92aa67f18f8c0401cdc6d4440ed512c43b131 (patch)
tree0a681b5f232105491183dfdb4efcc5d5d7050689 /src/lib/ector/software
parent4d6f20d714ea083471be163f67af518eced4028c (diff)
evas ector: add software implmentation for masking feature.
This implementation uses Ector_Buffer to generate mask image from vg container, and pass it to Ector engine. Ector renderer could blend this image as a mask. Yet only vg container works as a mask, we could extend shape to support masking later. Still vector gl drawing is not completed, We use software ector buffer to draw on it. This is on progessing.
Diffstat (limited to 'src/lib/ector/software')
-rw-r--r--src/lib/ector/software/ector_renderer_software_shape.c36
-rw-r--r--src/lib/ector/software/ector_renderer_software_shape.eo1
-rw-r--r--src/lib/ector/software/ector_software_buffer.c4
-rw-r--r--src/lib/ector/software/ector_software_private.h11
-rw-r--r--src/lib/ector/software/ector_software_rasterizer.c122
5 files changed, 150 insertions, 24 deletions
diff --git a/src/lib/ector/software/ector_renderer_software_shape.c b/src/lib/ector/software/ector_renderer_software_shape.c
index 6749d5fcb9..396e47283e 100644
--- a/src/lib/ector/software/ector_renderer_software_shape.c
+++ b/src/lib/ector/software/ector_renderer_software_shape.c
@@ -38,6 +38,9 @@ struct _Ector_Renderer_Software_Shape_Data
38 Shape_Rle_Data *shape_data; 38 Shape_Rle_Data *shape_data;
39 Shape_Rle_Data *outline_data; 39 Shape_Rle_Data *outline_data;
40 40
41 Ector_Buffer *mask;
42 int mask_op;
43
41 Ector_Software_Shape_Task *task; 44 Ector_Software_Shape_Task *task;
42 45
43 Eina_Bool done; 46 Eina_Bool done;
@@ -223,7 +226,7 @@ static void _outline_transform(Outline *outline, Eina_Matrix3 *m)
223static Eina_Bool 226static Eina_Bool
224_generate_outline(const Efl_Gfx_Path_Command *cmds, const double *pts, Outline * outline) 227_generate_outline(const Efl_Gfx_Path_Command *cmds, const double *pts, Outline * outline)
225{ 228{
226 Eina_Bool close_path = EINA_FALSE; 229 Eina_Bool close_path = EINA_FALSE;
227 for (; *cmds != EFL_GFX_PATH_COMMAND_TYPE_END; cmds++) 230 for (; *cmds != EFL_GFX_PATH_COMMAND_TYPE_END; cmds++)
228 { 231 {
229 switch (*cmds) 232 switch (*cmds)
@@ -661,16 +664,18 @@ _ector_renderer_software_shape_ector_renderer_draw(Eo *obj,
661 x = pd->surface->x + (int)pd->base->origin.x; 664 x = pd->surface->x + (int)pd->base->origin.x;
662 y = pd->surface->y + (int)pd->base->origin.y; 665 y = pd->surface->y + (int)pd->base->origin.y;
663 666
664 // fill the span_data structure
665 ector_software_rasterizer_clip_rect_set(pd->surface->rasterizer, clips); 667 ector_software_rasterizer_clip_rect_set(pd->surface->rasterizer, clips);
666 ector_software_rasterizer_transform_set(pd->surface->rasterizer, pd->base->m); 668 ector_software_rasterizer_transform_set(pd->surface->rasterizer, pd->base->m);
667 669
670 // fill the span_data structure
668 if (pd->shape->fill) 671 if (pd->shape->fill)
669 { 672 {
670 ector_renderer_software_op_fill(pd->shape->fill); 673 ector_renderer_software_op_fill(pd->shape->fill);
671 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer, 674 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer,
672 x, y, mul_col, op, 675 x, y, mul_col, op,
673 pd->shape_data); 676 pd->shape_data,
677 pd->mask,
678 pd->mask_op);
674 } 679 }
675 else 680 else
676 { 681 {
@@ -683,16 +688,22 @@ _ector_renderer_software_shape_ector_renderer_draw(Eo *obj,
683 pd->base->color.a); 688 pd->base->color.a);
684 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer, 689 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer,
685 x, y, mul_col, op, 690 x, y, mul_col, op,
686 pd->shape_data); 691 pd->shape_data,
692 pd->mask,
693 pd->mask_op);
687 } 694 }
688 } 695 }
689 696
697 if (!pd->outline_data) return EINA_TRUE;
698
690 if (pd->shape->stroke.fill) 699 if (pd->shape->stroke.fill)
691 { 700 {
692 ector_renderer_software_op_fill(pd->shape->stroke.fill); 701 ector_renderer_software_op_fill(pd->shape->stroke.fill);
693 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer, 702 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer,
694 x, y, mul_col, op, 703 x, y, mul_col, op,
695 pd->outline_data); 704 pd->outline_data,
705 pd->mask,
706 pd->mask_op);
696 } 707 }
697 else 708 else
698 { 709 {
@@ -705,7 +716,9 @@ _ector_renderer_software_shape_ector_renderer_draw(Eo *obj,
705 pd->public_shape->stroke.color.a); 716 pd->public_shape->stroke.color.a);
706 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer, 717 ector_software_rasterizer_draw_rle_data(pd->surface->rasterizer,
707 x, y, mul_col, op, 718 x, y, mul_col, op,
708 pd->outline_data); 719 pd->outline_data,
720 pd->mask,
721 pd->mask_op);
709 } 722 }
710 } 723 }
711 724
@@ -831,4 +844,15 @@ _ector_renderer_software_shape_ector_renderer_crc_get(const Eo *obj,
831 return crc; 844 return crc;
832} 845}
833 846
847static void
848_ector_renderer_software_shape_ector_renderer_mask_set(Eo *obj EINA_UNUSED,
849 Ector_Renderer_Software_Shape_Data *pd,
850 Ector_Buffer *mask,
851 int op)
852{
853 //Use ref/unref.
854 pd->mask = mask;
855 pd->mask_op = op;
856}
857
834#include "ector_renderer_software_shape.eo.c" 858#include "ector_renderer_software_shape.eo.c"
diff --git a/src/lib/ector/software/ector_renderer_software_shape.eo b/src/lib/ector/software/ector_renderer_software_shape.eo
index 97b15ca153..abe8344f3f 100644
--- a/src/lib/ector/software/ector_renderer_software_shape.eo
+++ b/src/lib/ector/software/ector_renderer_software_shape.eo
@@ -6,6 +6,7 @@ class Ector.Renderer.Software.Shape (Ector.Renderer.Software, Ector.Renderer.Sha
6 Ector.Renderer.prepare; 6 Ector.Renderer.prepare;
7 Ector.Renderer.draw; 7 Ector.Renderer.draw;
8 Ector.Renderer.Software.op_fill; 8 Ector.Renderer.Software.op_fill;
9 Ector.Renderer.mask { set; }
9 Ector.Renderer.crc { get; } 10 Ector.Renderer.crc { get; }
10 Efl.Gfx.Path.path { set; } 11 Efl.Gfx.Path.path { set; }
11 Efl.Object.constructor; 12 Efl.Object.constructor;
diff --git a/src/lib/ector/software/ector_software_buffer.c b/src/lib/ector/software/ector_software_buffer.c
index e8981281f5..e7d288e1e1 100644
--- a/src/lib/ector/software/ector_software_buffer.c
+++ b/src/lib/ector/software/ector_software_buffer.c
@@ -76,8 +76,8 @@ _ector_software_buffer_base_ector_buffer_pixels_set(Eo *obj, Ector_Software_Buff
76{ 76{
77 unsigned pxs; 77 unsigned pxs;
78 78
79 if (pd->generic->immutable) 79 //if (pd->generic->immutable)
80 fail("This buffer is immutable."); 80// fail("This buffer is immutable.");
81 81
82 if (pd->internal.maps) 82 if (pd->internal.maps)
83 fail("Can not call pixels_set when the buffer is mapped."); 83 fail("Can not call pixels_set when the buffer is mapped.");
diff --git a/src/lib/ector/software/ector_software_private.h b/src/lib/ector/software/ector_software_private.h
index dad1f9948c..34ea0038b7 100644
--- a/src/lib/ector/software/ector_software_private.h
+++ b/src/lib/ector/software/ector_software_private.h
@@ -82,9 +82,11 @@ typedef struct _Span_Data
82 82
83 int offx, offy; 83 int offx, offy;
84 Clip_Data clip; 84 Clip_Data clip;
85 Ector_Software_Buffer_Base_Data *mask;
86 int mask_op;
85 Eina_Matrix3 inv; 87 Eina_Matrix3 inv;
86 Span_Data_Type type; 88 Span_Data_Type type;
87 Eina_Bool fast_matrix ; 89 Eina_Bool fast_matrix;
88 uint32_t mul_col; 90 uint32_t mul_col;
89 Efl_Gfx_Render_Op op; 91 Efl_Gfx_Render_Op op;
90 union { 92 union {
@@ -129,7 +131,12 @@ void ector_software_rasterizer_clip_shape_set(Software_Rasterizer *rasterizer, S
129Shape_Rle_Data * ector_software_rasterizer_generate_rle_data(Ector_Software_Thread *thread, Software_Rasterizer *rasterizer, SW_FT_Outline *outline); 131Shape_Rle_Data * ector_software_rasterizer_generate_rle_data(Ector_Software_Thread *thread, Software_Rasterizer *rasterizer, SW_FT_Outline *outline);
130Shape_Rle_Data * ector_software_rasterizer_generate_stroke_rle_data(Ector_Software_Thread *thread, Software_Rasterizer *rasterizer, SW_FT_Outline *outline, Eina_Bool closePath); 132Shape_Rle_Data * ector_software_rasterizer_generate_stroke_rle_data(Ector_Software_Thread *thread, Software_Rasterizer *rasterizer, SW_FT_Outline *outline, Eina_Bool closePath);
131 133
132void ector_software_rasterizer_draw_rle_data(Software_Rasterizer *rasterizer, int x, int y, uint32_t mul_col, Efl_Gfx_Render_Op op, Shape_Rle_Data* rle); 134void ector_software_rasterizer_draw_rle_data(Software_Rasterizer *rasterizer,
135 int x, int y, uint32_t mul_col,
136 Efl_Gfx_Render_Op op,
137 Shape_Rle_Data* rle,
138 Ector_Buffer *mask,
139 int mask_op);
133 140
134void ector_software_rasterizer_destroy_rle_data(Shape_Rle_Data *rle); 141void ector_software_rasterizer_destroy_rle_data(Shape_Rle_Data *rle);
135 142
diff --git a/src/lib/ector/software/ector_software_rasterizer.c b/src/lib/ector/software/ector_software_rasterizer.c
index 25169be790..7a03bb69f2 100644
--- a/src/lib/ector/software/ector_software_rasterizer.c
+++ b/src/lib/ector/software/ector_software_rasterizer.c
@@ -14,22 +14,100 @@
14static void 14static void
15_blend_color_argb(int count, const SW_FT_Span *spans, void *user_data) 15_blend_color_argb(int count, const SW_FT_Span *spans, void *user_data)
16{ 16{
17 RGBA_Comp_Func_Solid comp_func; 17 Span_Data *sd = user_data;
18 Span_Data *data = (Span_Data *)(user_data);
19 uint32_t color, *buffer, *target; 18 uint32_t color, *buffer, *target;
20 const int pix_stride = data->raster_buffer->stride / 4; 19 const int pix_stride = sd->raster_buffer->stride / 4;
21 20
22 // multiply the color with mul_col if any 21 // multiply the color with mul_col if any
23 color = DRAW_MUL4_SYM(data->color, data->mul_col); 22 color = DRAW_MUL4_SYM(sd->color, sd->mul_col);
24 comp_func = efl_draw_func_solid_span_get(data->op, color); 23 RGBA_Comp_Func_Solid comp_func = efl_draw_func_solid_span_get(sd->op, color);
25 24
26 // move to the offset location 25 // move to the offset location
27 buffer = data->raster_buffer->pixels.u32 + ((pix_stride * data->offy) + data->offx); 26 buffer = sd->raster_buffer->pixels.u32 + ((pix_stride * sd->offy) + sd->offx);
27
28 while (count--)
29 {
30 target = buffer + ((pix_stride * spans->y) + spans->x);
31 comp_func(target, spans->len, color, spans->coverage);
32 ++spans;
33 }
34}
35
36static void
37_blend_color_argb_with_maskA(int count, const SW_FT_Span *spans, void *user_data)
38{
39 Span_Data *sd = user_data;
40 const int pix_stride = sd->raster_buffer->stride / 4;
41 Ector_Software_Buffer_Base_Data *mask = sd->mask;
42
43 // multiply the color with mul_col if any
44 uint32_t color = DRAW_MUL4_SYM(sd->color, sd->mul_col);
45 RGBA_Comp_Func_Solid comp_func = efl_draw_func_solid_span_get(sd->op, color);
46
47 // move to the offset location
48 uint32_t *buffer =
49 sd->raster_buffer->pixels.u32 + ((pix_stride * sd->offy) + sd->offx);
50 uint32_t *mbuffer = mask->pixels.u32;
28 51
29 while (count--) 52 while (count--)
30 { 53 {
31 target = buffer + ((pix_stride * spans->y) + spans->x); 54 uint32_t *target = buffer + ((pix_stride * spans->y) + spans->x);
32 comp_func(target, spans->len, color, spans->coverage); 55 uint32_t *mtarget =
56 mbuffer + ((mask->generic->w * spans->y) + spans->x);
57 uint32_t *temp = alloca(sizeof(uint32_t) * spans->len);
58 memset(temp, 0x00, sizeof(uint32_t) * spans->len);
59 comp_func(temp, spans->len, color, spans->coverage);
60
61 //masking
62 for (int i = 0; i < spans->len; i++)
63 {
64 *temp = draw_mul_256(((*mtarget)>>24), *temp);
65 int alpha = 255 - ((*temp) >> 24);
66 *target = *temp + draw_mul_256(alpha, *target);
67 ++temp;
68 ++mtarget;
69 ++target;
70 }
71 ++spans;
72 }
73}
74
75static void
76_blend_color_argb_with_maskInvA(int count, const SW_FT_Span *spans, void *user_data)
77{
78 Span_Data *sd = user_data;
79 const int pix_stride = sd->raster_buffer->stride / 4;
80 Ector_Software_Buffer_Base_Data *mask = sd->mask;
81
82 // multiply the color with mul_col if any
83 uint32_t color = DRAW_MUL4_SYM(sd->color, sd->mul_col);
84 RGBA_Comp_Func_Solid comp_func = efl_draw_func_solid_span_get(sd->op, color);
85
86 // move to the offset location
87 uint32_t *buffer =
88 sd->raster_buffer->pixels.u32 + ((pix_stride * sd->offy) + sd->offx);
89 uint32_t *mbuffer = mask->pixels.u32;
90
91 while (count--)
92 {
93 uint32_t *target = buffer + ((pix_stride * spans->y) + spans->x);
94 uint32_t *mtarget =
95 mbuffer + ((mask->generic->w * spans->y) + spans->x);
96 uint32_t *temp = alloca(sizeof(uint32_t) * spans->len);
97 memset(temp, 0x00, sizeof(uint32_t) * spans->len);
98 comp_func(temp, spans->len, color, spans->coverage);
99
100 //masking
101 for (int i = 0; i < spans->len; i++)
102 {
103 if (*mtarget)
104 *temp = draw_mul_256((255 - ((*mtarget)>>24)), *temp);
105 int alpha = 255 - ((*temp) >> 24);
106 *target = *temp + draw_mul_256(alpha, *target);
107 ++temp;
108 ++mtarget;
109 ++target;
110 }
33 ++spans; 111 ++spans;
34 } 112 }
35} 113}
@@ -267,13 +345,24 @@ _span_fill_clipPath(int span_count, const SW_FT_Span *spans, void *user_data)
267static void 345static void
268_adjust_span_fill_methods(Span_Data *spdata) 346_adjust_span_fill_methods(Span_Data *spdata)
269{ 347{
348 //Blending Function
270 switch(spdata->type) 349 switch(spdata->type)
271 { 350 {
272 case None: 351 case None:
273 spdata->unclipped_blend = 0; 352 spdata->unclipped_blend = NULL;
274 break; 353 break;
275 case Solid: 354 case Solid:
276 spdata->unclipped_blend = &_blend_color_argb; 355 {
356 if (spdata->mask)
357 {
358 if (spdata->mask_op == 2)
359 spdata->unclipped_blend = &_blend_color_argb_with_maskInvA;
360 else
361 spdata->unclipped_blend = &_blend_color_argb_with_maskA;
362 }
363 else
364 spdata->unclipped_blend = &_blend_color_argb;
365 }
277 break; 366 break;
278 case LinearGradient: 367 case LinearGradient:
279 case RadialGradient: 368 case RadialGradient:
@@ -539,17 +628,22 @@ ector_software_rasterizer_radial_gradient_set(Software_Rasterizer *rasterizer,
539 rasterizer->fill_data.type = RadialGradient; 628 rasterizer->fill_data.type = RadialGradient;
540} 629}
541 630
542void ector_software_rasterizer_draw_rle_data(Software_Rasterizer *rasterizer, 631void
543 int x, int y, uint32_t mul_col, 632ector_software_rasterizer_draw_rle_data(Software_Rasterizer *rasterizer,
544 Efl_Gfx_Render_Op op, Shape_Rle_Data* rle) 633 int x, int y, uint32_t mul_col,
634 Efl_Gfx_Render_Op op, Shape_Rle_Data* rle,
635 Ector_Buffer *mask,
636 int mask_op)
545{ 637{
546 // check for NULL rle data
547 if (!rle) return; 638 if (!rle) return;
548 639
549 rasterizer->fill_data.offx = x; 640 rasterizer->fill_data.offx = x;
550 rasterizer->fill_data.offy = y; 641 rasterizer->fill_data.offy = y;
551 rasterizer->fill_data.mul_col = mul_col; 642 rasterizer->fill_data.mul_col = mul_col;
552 rasterizer->fill_data.op = op; 643 rasterizer->fill_data.op = op;
644 rasterizer->fill_data.mask =
645 mask ? efl_data_scope_get(mask, ECTOR_SOFTWARE_BUFFER_BASE_MIXIN) : NULL;
646 rasterizer->fill_data.mask_op = mask_op;
553 647
554 _setup_span_fill_matrix(rasterizer); 648 _setup_span_fill_matrix(rasterizer);
555 _adjust_span_fill_methods(&rasterizer->fill_data); 649 _adjust_span_fill_methods(&rasterizer->fill_data);